@postnord/web-components
Version:
PostNord Web Components
274 lines (273 loc) • 10.6 kB
JavaScript
/*!
* Built with Stencil
* By PostNord.
*/
import { h, Host } from "@stencil/core";
import { translations } from "./translations";
import { en, awaitTopbar, uuidv4 } from "../../../globals/helpers";
/**
* The `pn-progress-stepper` is used to visualize the users progress through a flow (checkout/survey, etc...).
**/
export class PnProgressStepper {
id = `pn-progress-stepper-${uuidv4()}`;
idLabel = `${this.id}-label`;
idBar = `${this.id}-bar`;
minStep = 1;
maxStep = 7;
hostElement;
/** Percentage calculated with currentStep / totalSteps. */
progressValue = 0;
/** Set custom label for the stepper, recommended default label is "Step". */
label;
/** Set total amount of steps, maximum `7` is allowed. */
totalSteps = this.maxStep;
/** The current step of the progress stepper. */
currentStep = this.minStep;
/** You can add a custom optional string to the label if you need a name for the current step. */
stepName;
/** Set a custom HTML id on the progress stepper element to associate progress bar with label. */
progressStepperId = '';
/**
* Set the language manually, only use this prop if the pnTopbar is not loaded.
* Will not overwrite the `label` prop if used.
**/
language = null;
validateCurrentStep(step) {
this.validate(step, 'currentStep');
}
validateTotalSteps(step) {
this.validate(step, 'totalSteps');
}
watchLanguage() {
if (this.hasCustomLabel())
return;
this.label = translations.STEP[this.language || en];
}
watchId() {
if (this.progressStepperId) {
this.idLabel = `${this.progressStepperId}-label`;
this.idBar = `${this.progressStepperId}-bar`;
}
else {
this.idLabel = `${this.id}-label`;
this.idBar = `${this.id}-bar`;
}
}
async componentWillLoad() {
this.watchLanguage();
this.watchId();
this.validate(this.currentStep, 'currentStep');
this.validate(this.totalSteps, 'totalSteps');
if (this.language)
return;
await awaitTopbar(this.hostElement);
}
componentWillRender() {
this.calculateProgress();
}
hasCustomLabel() {
if (this.label === undefined)
return false;
return !Object.keys(translations.STEP).find(step => translations.STEP[step] === this.label);
}
validate(step, prop) {
const componentName = this.hostElement.localName;
if (step < this.minStep) {
console.warn(`${componentName}: The ${prop} ${step} is below the minimum allowed steps of ${this.minStep}. ${prop} will default to ${this.minStep}.`);
this[prop] = this.minStep;
}
if (prop === 'currentStep' && step > this.totalSteps) {
console.warn(`${componentName}: The ${prop} ${step} is above totalSteps ${this.totalSteps}, ${prop} will default to ${this.totalSteps}.`);
this[prop] = this.totalSteps;
}
if (step > this.maxStep) {
console.warn(`${componentName}: The ${prop} ${step} is above the maximum allowed steps of ${this.maxStep}. ${prop} will default to ${this.maxStep}.`);
this[prop] = this.maxStep;
}
}
calculateProgress() {
try {
this.progressValue = Math.floor((this.currentStep / this.totalSteps) * 100);
this.hostElement.style.setProperty('--progress-value', `${this.progressValue}%`);
}
catch (error) {
console.error(`${this.hostElement.localName}:`, error.message);
}
}
render() {
return (h(Host, { key: '272d1f3abc78f82d1d047b54e0367067f9487dae' }, h("p", { key: '129f4fb4d853db711d059c0d23d10524b0633394', id: this.idLabel, class: "pn-progress-stepper-label" }, h("span", { key: '8fb640f99c63b4fdaa2eb6eb1a580b0dd590b75c' }, this.label, " ", this.currentStep, "/", this.totalSteps), this.stepName && h("span", { key: 'e6aab7895bbb0b040fec057fdc52a377dcadfae2' }, " - ", this.stepName)), h("div", { key: 'e21d798014f01c850d4a90fc525d4ce03fc76705', class: "pn-progress-stepper", role: "progressbar", "aria-labelledby": this.idLabel, "aria-valuenow": this.progressValue, id: this.idBar, "data-full": this.currentStep === this.totalSteps }, h("div", { key: 'db86f96f1e1ab1f7e62fb0b2b2b1dfee24647983', class: "pn-progress-stepper-value" }))));
}
static get is() { return "pn-progress-stepper"; }
static get originalStyleUrls() {
return {
"$": ["pn-progress-stepper.scss"]
};
}
static get styleUrls() {
return {
"$": ["pn-progress-stepper.css"]
};
}
static get properties() {
return {
"label": {
"type": "string",
"mutable": true,
"complexType": {
"original": "string",
"resolved": "string",
"references": {}
},
"required": false,
"optional": true,
"docs": {
"tags": [],
"text": "Set custom label for the stepper, recommended default label is \"Step\"."
},
"getter": false,
"setter": false,
"attribute": "label",
"reflect": false
},
"totalSteps": {
"type": "number",
"mutable": true,
"complexType": {
"original": "PnSteps",
"resolved": "1 | 2 | 3 | 4 | 5 | 6 | 7",
"references": {
"PnSteps": {
"location": "import",
"path": "@/globals/types",
"id": "src/globals/types.ts::PnSteps"
}
}
},
"required": false,
"optional": false,
"docs": {
"tags": [],
"text": "Set total amount of steps, maximum `7` is allowed."
},
"getter": false,
"setter": false,
"attribute": "total-steps",
"reflect": false,
"defaultValue": "this.maxStep"
},
"currentStep": {
"type": "number",
"mutable": true,
"complexType": {
"original": "PnSteps",
"resolved": "1 | 2 | 3 | 4 | 5 | 6 | 7",
"references": {
"PnSteps": {
"location": "import",
"path": "@/globals/types",
"id": "src/globals/types.ts::PnSteps"
}
}
},
"required": false,
"optional": false,
"docs": {
"tags": [],
"text": "The current step of the progress stepper."
},
"getter": false,
"setter": false,
"attribute": "current-step",
"reflect": false,
"defaultValue": "this.minStep"
},
"stepName": {
"type": "string",
"mutable": false,
"complexType": {
"original": "string",
"resolved": "string",
"references": {}
},
"required": false,
"optional": true,
"docs": {
"tags": [],
"text": "You can add a custom optional string to the label if you need a name for the current step."
},
"getter": false,
"setter": false,
"attribute": "step-name",
"reflect": false
},
"progressStepperId": {
"type": "string",
"mutable": false,
"complexType": {
"original": "string",
"resolved": "string",
"references": {}
},
"required": false,
"optional": true,
"docs": {
"tags": [],
"text": "Set a custom HTML id on the progress stepper element to associate progress bar with label."
},
"getter": false,
"setter": false,
"attribute": "progress-stepper-id",
"reflect": false,
"defaultValue": "''"
},
"language": {
"type": "string",
"mutable": false,
"complexType": {
"original": "PnLanguages",
"resolved": "\"\" | \"da\" | \"en\" | \"fi\" | \"no\" | \"sv\"",
"references": {
"PnLanguages": {
"location": "import",
"path": "@/globals/types",
"id": "src/globals/types.ts::PnLanguages"
}
}
},
"required": false,
"optional": true,
"docs": {
"tags": [],
"text": "Set the language manually, only use this prop if the pnTopbar is not loaded.\nWill not overwrite the `label` prop if used."
},
"getter": false,
"setter": false,
"attribute": "language",
"reflect": false,
"defaultValue": "null"
}
};
}
static get states() {
return {
"progressValue": {}
};
}
static get elementRef() { return "hostElement"; }
static get watchers() {
return [{
"propName": "currentStep",
"methodName": "validateCurrentStep"
}, {
"propName": "totalSteps",
"methodName": "validateTotalSteps"
}, {
"propName": "language",
"methodName": "watchLanguage"
}, {
"propName": "progressStepperId",
"methodName": "watchId"
}];
}
}
//# sourceMappingURL=pn-progress-stepper.js.map