Skip to content

Commit

Permalink
Merge branch 'develop'
Browse files Browse the repository at this point in the history
  • Loading branch information
maaaaarco committed May 10, 2019
2 parents c63ca0c + 9a2e691 commit 7e97aa4
Show file tree
Hide file tree
Showing 22 changed files with 12,915 additions and 0 deletions.
6 changes: 6 additions & 0 deletions .eslintignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
**/lwc/**/*.css
**/lwc/**/*.html
**/lwc/**/*.json
**/lwc/**/*.svg
**/lwc/**/*.xml
.sfdx
18 changes: 18 additions & 0 deletions .forceignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# List files or directories below to ignore them when running force:source:push, force:source:pull, and force:source:status
# More information: https://developer.salesforce.com/docs/atlas.en-us.sfdx_dev.meta/sfdx_dev/sfdx_dev_exclude_source.htm
#

# Standard metadata
package.xml
**appMenu
**appSwitcher
**objectTranslations
**profiles
**settings

# LWC configuration files
**/jsconfig.json
**/.eslintrc.json

# LWC Jest
**/__tests__/**
37 changes: 37 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# This file is used for Git repositories to specify intentionally untracked files that Git should ignore.
# If you are not using git, you can delete this file. For more information see: https://git-scm.com/docs/gitignore
# For useful gitignore templates see: https://github.com/github/gitignore

# Salesforce cache
.sfdx/

# LWC VSCode autocomplete
jsconfig.json

# LWC Jest coverage reports
coverage/

# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*

# Dependency directories
node_modules/

# Eslint cache
.eslintcache

# MacOS system files
.DS_Store

# Windows system files
Thumbs.db
ehthumbs.db
[Dd]esktop.ini
$RECYCLE.BIN/

# VS Code project settings
.vscode/
6 changes: 6 additions & 0 deletions .prettierignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
# List files or directories below to ignore them when running prettier
# More information: https://prettier.io/docs/en/ignore.html
#

**/staticresources/**
.sfdx
15 changes: 15 additions & 0 deletions .prettierrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{
"trailingComma": "none",
"singleQuote": true,
"tabWidth": 4,
"overrides": [
{
"files": "**/lwc/**/*.html",
"options": { "parser": "lwc" }
},
{
"files": "*.{cmp,page,component}",
"options": { "parser": "html" }
}
]
}
51 changes: 51 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,2 +1,53 @@
# Salesforce-Custom-Path-Assistant-LWC

A custom path assistant built using only Lightning Web Components

## Reasons

Main reason for this project is that currently is not possible to replicate the same look and feel of the Opportunity Sales Path using custom Path Assistants.
When you create a new Path Assistant you can specify an Object, a picklist field and a record type... What you miss is the ability to defines which picklist values are mutually exclusive at the end of the path.

## Example

We have a Project Object used to track the different implementation projects related to specified customers. Each Project record has a Status that can be:

- New
- In progress
- On hold
- Completed
- Failed

We want to display the Status as a path on the Project record page. We want the path to be green in case the status is Completed, red in case the status is Failed.
If we create a Path Assistant and then add the standard _Path_ Lightning component to the record page this is what we get:

![alt text](./doc/images/projectStatus.png 'Project status')

Not really want we wanted! As you can see both values _Completed_ and _Failed_ are displayed. Even worst seems that _Failed_ is the status that comes after _Completed_.

Without creating the Path Assistant we can instead use the custom Lightning Component called _pathAssistant_.
In the Lightning App Builder drag and drop the custom component on the record page and fill the form on the right like this:

![alt text](./doc/images/appBuilder.png 'App Builder')

This is the result on the record page

![alt text](./doc/images/initialStatus.png 'Initial Status')

Users can now select the final _Closed_ status and after pressing on the button _Select Closed Status_ they'll be able to select the proper value

![alt text](./doc/images/selectClosed.png 'Select Closed')

![alt text](./doc/images/modal.png 'Modal')

Depending on the final status they pick these can be the results:

![alt text](./doc/images/completed.png 'Completed')

![alt text](./doc/images/failed.png 'Failed')

## Considerations

This Lightning Web Component is fully aware of its context when added to a Record page. This means that it's not object specific and can be added on any object that has a picklist field.
It doesn't need to use an Apex controller thanks to the _uiRecordApi_ module that provides method to update and retrieve records.
In case your object has multiple record types the picklist values displayed are the one you enabled for it (same as standard Path Assistant).
The only requirements this component has is that the picklist field, on which the path is based, has to be included in the Page Layout of the object.
10 changes: 10 additions & 0 deletions config/project-scratch-def.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
{
"orgName": "mzeuli Company",
"edition": "Developer",
"features": [],
"settings": {
"orgPreferenceSettings": {
"s1DesktopEnabled": true
}
}
}
Binary file added doc/images/appBuilder.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added doc/images/completed.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added doc/images/failed.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added doc/images/initialStatus.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added doc/images/modal.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added doc/images/projectStatus.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added doc/images/selectClosed.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions force-app/main/default/lwc/.eslintrc.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"extends": "@salesforce/eslint-config-lwc/recommended"
}
188 changes: 188 additions & 0 deletions force-app/main/default/lwc/pathAssistant/pathAssistant.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,188 @@
<template>
<!-- error alert -->
<div
if:true={errorMsg}
class="slds-notify slds-notify_alert slds-theme_alert-texture slds-theme_error"
role="alert"
>
<span class="slds-assistive-text">error</span>
<span
class="slds-icon_container slds-icon-utility-error slds-m-right_x-small"
title="Description of icon when needed"
>
<lightning-icon
icon-name="utility:error"
size="small"
></lightning-icon>
</span>
<h2>
{genericErrorMessage}
</h2>
<p>
{errorMsg}
</p>
</div>

<article if:false={errorMsg} class="slds-card">
<!-- path assistant -->
<div class="slds-path">
<div class="slds-grid slds-path__track">
<div class="slds-grid slds-path__scroller-container">
<div class="slds-path__scroller" role="application">
<div class="slds-path__scroller_inner">
<!-- spinner -->
<lightning-spinner
variant="brand"
size="small"
if:true={hasToShowSpinner}
>
</lightning-spinner>

<ul
if:true={isLoaded}
class="slds-path__nav"
role="listbox"
aria-orientation="horizontal"
>
<template for:each={steps} for:item="step">
<li
key={step.value}
class={step.classText}
role="presentation"
>
<a
aria-selected="false"
class="slds-path__link"
href="javascript:void(0);"
role="option"
tabindex="-1"
data-value={step.value}
onclick={handleStepSelected}
>
<span class="slds-path__stage">
<lightning-icon
icon-name="utility:check"
size="xx-small"
variant="inverse"
></lightning-icon>
</span>
<span class="slds-path__title"
>{step.label}</span
>
</a>
</li>
</template>
</ul>
</div>
</div>
</div>
<div
if:false={hideUpdateButton}
class="slds-grid slds-path__action"
>
<template if:true={isLoaded}>
<!-- button enabled -->
<button
if:false={isUpdateButtonDisabled}
type="button"
class="slds-button slds-button_brand slds-path__mark-complete"
onclick={handleUpdateButtonClick}
>
{updateButtonText}
</button>

<!-- button disabled -->
<button
if:true={isUpdateButtonDisabled}
type="button"
class="slds-button slds-button_brand slds-path__mark-complete"
disabled="disabled"
>
{updateButtonText}
</button>
</template>
</div>
</div>
</div>
</article>

<!-- modal to select a closed step -->
<section
if:true={openModal}
role="dialog"
tabindex="-1"
aria-labelledby="modal-heading-01"
aria-modal="true"
aria-describedby="modal-content-id-1"
class="slds-modal slds-fade-in-open slds-modal_small"
>
<div class="slds-modal__container">
<header class="slds-modal__header">
<button
class="slds-button slds-button_icon slds-modal__close slds-button_icon-inverse"
title="Close"
onclick={closeModal}
>
<lightning-icon
icon-name="utility:close"
variant="inverse"
size="medium"
></lightning-icon>
<span class="slds-assistive-text">Close</span>
</button>
<h2
id="modal-heading-01"
class="slds-text-heading_medium slds-hyphenate"
>
{modalHeader}
</h2>
</header>
<div
class="slds-modal__content slds-p-around_medium"
id="modal-content-id-1"
>
<div class="slds-form-element">
<label class="slds-form-element__label" for="select-01">
<abbr class="slds-required" title="required">*</abbr
>{selectLabel}
</label>
<div class="slds-form-element__control">
<div class="slds-select_container">
<select
class="slds-select"
id="select-01"
required=""
onchange={setClosedStep}
>
<option value="">--- None ---</option>
<template
for:each={closedSteps}
for:item="step"
>
<option key={step.index} value={step.value}
>{step.label}</option
>
</template>
</select>
</div>
</div>
</div>
</div>
<footer class="slds-modal__footer">
<button
class="slds-button slds-button_neutral"
onclick={closeModal}
>
Cancel
</button>
<button
class="slds-button slds-button_brand"
onclick={handleSaveButtonClick}
>
Save
</button>
</footer>
</div>
</section>
<div if:true={openModal} class="slds-backdrop slds-backdrop_open"></div>
</template>
Loading

0 comments on commit 7e97aa4

Please sign in to comment.