Background
With the recent popularity of SPFx, developers are required to develop some complex requirements using the SharePoint framework web part. Many of these requirements are common and need to be developed again and again. Microsoft has provided
Office UI fabric react based controls which can be easily used in our SPFx web part. Still, there are some controls that are missing in Office UI fabric, thanks to our awesome PnP initiative, the community has stepped forward and developed many more controls that can be used in our SPFx solutions.
You can know and read about all the controls available from PnP controls library at this
link. Today we will learn about Listitem picker control of PnP and how it can be utilized in SPFx webpart.
Scenario
Suppose you are developing a SPFx webpart custom form to get data from the user. Many times, we would need to bind lookup columns (master data) in the dropdown to allow users to select. Traditionally what we would do is create a dropdown control and bind its options by querying master list (one of the columns would be bound as key and another as a display value). In such cases, we can use
PnP ListItemPicker control which does the heavy lifting of binding values to control by calling rest api internally and binding the id and value column as per our configuration. Let us see how to do it.
Let's get started and create web part.
Step - Create SPFx solution and webpart
Run below commands in sequence.
Open a node js command prompt and create a directory for SPFx solution.
- md PnPControlsDemo
- cd PnPControlsDemo
Let us now create SPFx solution and add web part to it.
Please select below options, please note we need to choose React framework as this control is based on react.
Once you select all options in wizard one by one, it will take some time to generate the code structure.
Now let us install required npm packages to use PnP controls. run below command.
- npm install @pnp/spfx-controls-react --save
After it is completed, open same folder in Visual Studio code( you can use any other editor also).
Now let us modify code to use these controls.
Step - Passing WebPart context to React components
ListItem Picker control requires Sharepoint site context to work with, hence we will pass it from our web part file to react components.
Open src\webparts\controls\components\IControlsProps.ts
Modify code to below,
- import { WebPartContext } from '@microsoft/sp-webpart-base';
- export interface IControlsProps {
- description: string;
- context: WebPartContext;
- }
Open src\webparts\controls\ControlsWebPart.ts
Modify render method to pass context.
- public render(): void {
- const element: React.ReactElement<IControlsProps > = React.createElement(
- Controls,
- {
- description: this.properties.description,
- context:this.context
- }
- );
- ReactDom.render(element, this.domElement);
Please note we have just added line 'context:this.context' .
Step - Modify the React component associated with webpart
Open src\webparts\controls\components\Controls.tsx
Import list item picker control and a button from office-ui-fabric-react
- import { ListItemPicker } from '@pnp/spfx-controls-react/lib/listItemPicker';
- import { PrimaryButton } from 'office-ui-fabric-react';
Create Interface to Store State, add below code below last import statement,
- export interface IControlsState {
- selectedValues:any[];
- }
Modify component as below,
- export default class Controls extends React.Component<IControlsProps, IControlsState> {
-
- constructor(props: IControlsProps, state: IControlsState) {
- super(props);
- this.state = {selectedValues:[]};
- }
-
- .......
Modify the render method, refer below code and modify as per your requirement,
- public render(): React.ReactElement<IControlsProps> {
- return (
- <div className={ styles.controls }>
- <div className={ styles.container }>
- <div className={ styles.row }>
- <div className={ styles.column }>
- <span className={ styles.title }>Welcome to SharePoint!</span>
- <p className={ styles.subTitle }>Customize SharePoint experiences using Web Parts.</p>
- <p className={ styles.description }>{escape(this.props.description)}</p>
- <a href="https://aka.ms/spfx" className={ styles.button }>
- <span className={ styles.label }>Learn more</span>
- </a>
- </div>
- </div>
- </div>
- <br></br>
- Select Asset
- <ListItemPicker listId='ba682bc2-351e-45ae-8cbe-b0512ba0291a'
- columnInternalName='Title'
- keyColumnInternalName='Id'
- itemLimit={2}
- onSelectedItem={this.onSelectedItem}
- context={this.props.context}
- suggestionsHeaderText = "Please select asset"
- />
- <br></br>
- <PrimaryButton text="Submit" onClick={this.submitClicked} />
-
- </div>
- );
- }
Now let us see, what different attribute means in the below code,
- ListId - GUID of list from which we need to display values in control.
- ColumnInternalName - Internal name of column which you need to display.
- KeyColumnInternamName - Internal name of column which you wanted to use as key, in most case this will be ID column.
- itemLimit - this is a maximum number of item we want user to select. If you need single-valued, set this to 1.
Others are pretty self explanatory
Now let us add a method to set state when user will select values in control.
Here we are overriding state variable as soon as selected or changed in control.
- private onSelectedItem = (data: { key: string; name: string }[]) :void=>{
- this.setState({selectedValues:data});
- }
Now let us write event which handle submit button click and display selected values in alert box by reading from state.
- private submitClicked = ():void => {
- alert(JSON.stringify(this.state.selectedValues)) ;
- }
Please note that, I am using below List as master data to display values in control.
We are done with code, now let us run it. Use gulp serve command in node js command prompt. Please note that this control requires the context of SharePoint site because it has to display list items from SharePoint list. So we will test this webpart in SharePoint workbench.
Once local workbench is opened in the browser, open SharePoint workbench.
https://amazonprime.sharepoint.com/sites/war/_layouts/15/workbench.aspx
Below is the output of web part.
Start typing in Select asset control.
Once you select one or more values and click on submit we can see the selected values are displayed in alert.
Conclusion
This control can be very useful as we don't have to write repetitive code to display master data in dropdown and added advantage is that it provide auto-complete feature. Use this reduce your development time :)
Thanks for reading, hope this helps..Happy coding..!!