Salesforce LWC学习(二十二) 简单知识总结篇二
本篇参看:
https://developer.salesforce.com/docs/component-library/documentation/en/lwc/lwc.reactivity_fields
碰到之前接触的记录一下,深化一下印象。
一. 解决 lightning-record-edit-form没有入力时,效果和标准不一样的问题
先看一下标准的创建数据的UI,当有必入力字段的表单,点击Save按钮以后,上部会有DIV提示。
我们使用 lightning-record-edit-form实现时,发现onsubmit这种 handler需要再所有的字段都满足情况下才执行,也就是说页面中有 invalid的字段入力情况下,不会提交表单,也自然无法执行 onsubmit对应的方法。这个时候,我们就需要在submit的这个按钮添加 onclick方法去调用后台从而实现尽管提交不了表单还可以正常做一些UI效果的可能。简单代码如下
accountEditWithEditForm.html: 展示两个字段,save button除了在submit基础上,还有 onclick操作。需要注意的是, onclick会先于 onsubmit执行,所以我们可以在 onclick做一些validation操作,成功的话,让onsubmit正常执行表单提交操作。
<template> <lightning-record-edit-form record-id={recordId} object-api-name="Account" onsubmit={handleSubmit} > <lightning-messages></lightning-messages> <c-error-message-modal is-show-error-div={isShowErrorDiv} error-message-list={errorMessageList}></c-error-message-modal> <lightning-layout multiple-rows="true"> <lightning-layout-item size="6"> <lightning-input-field field-name="Name"></lightning-input-field> </lightning-layout-item> <lightning-layout-item size="6"> <lightning-input-field field-name="AnnualRevenue"></lightning-input-field> </lightning-layout-item> <lightning-layout-item size="12"> <div class="slds-m-top_medium"> <lightning-button class="slds-m-top_small" label="Cancel" onclick={handleReset}></lightning-button> <lightning-button class="slds-m-top_small" type="submit" label="Save Record" onclick={handleClick}></lightning-button> </div> </lightning-layout-item> </lightning-layout> </lightning-record-edit-form> </template>
accountEditWithEditForm.js
import { LightningElement,track,api,wire } from 'lwc'; import { updateRecord,getRecord } from 'lightning/uiRecordApi'; import { ShowToastEvent } from 'lightning/platformShowToastEvent'; import { NavigationMixin } from 'lightning/navigation'; import { navigationWhenErrorOccur } from 'c/navigationUtils'; import {isSystemOrCustomError,getPageCustomErrorMessageList,getFieldCustomErrorMessageList} from 'c/errorCheckUtils'; import ACCOUNT_ID_FIELD from '@salesforce/schema/Account.Id'; import ACCOUNT_NAME_FIELD from '@salesforce/schema/Account.Name'; import ACCOUNT_ANNUALREVENUE_FIELD from '@salesforce/schema/Account.AnnualRevenue'; const fields = [ ACCOUNT_ID_FIELD, ACCOUNT_NAME_FIELD, ACCOUNT_ANNUALREVENUE_FIELD ]; export default class AccountEditWithEditForm extends NavigationMixin(LightningElement) { @api recordId = '0010I00002U8dBPQAZ'; @track isShowErrorDiv = false; @track errorMessageList = []; @track isFormValid = true; handleSubmit(event) { event.preventDefault(); if(!this.isShowErrorDiv) { const fields = {}; fields[ACCOUNT_ID_FIELD.fieldApiName] = this.recordId; fields[ACCOUNT_NAME_FIELD.fieldApiName] = event.detail.Name; fields[ACCOUNT_ANNUALREVENUE_FIELD.fieldApiName] = event.detail.AnnualRevenue; const recordInput = { fields }; this.errorMessageList = []; this.isShowErrorDiv = false; updateRecord(recordInput) .then(() => { this.dispatchEvent( new ShowToastEvent({ title: 'Success', message: 'Account updated', variant: 'success' }) ); }).catch(error => { let systemOrCustomError = isSystemOrCustomError(error); if(systemOrCustomError) { navigationWhenErrorOccur(this,error); } else { this.isShowErrorDiv = true; this.errorMessageList = getPageCustomErrorMessageList(error); console.log(JSON.stringify(this.errorMessageList)); let errorList = getFieldCustomErrorMessageList(error); if(errorList && errorList.length > 0) { errorList.forEach(field => { this.reportValidityForField(field.key,field.value); }); } } }); } } handleClick(event) { let allInputList = Array.from(this.template.querySelectorAll('lightning-input-field')); let invalidFieldLabel = []; const allValid = allInputList.forEach(field => { if(field.required && field.value === '') { invalidFieldLabel.push(field.fieldName); this.isShowErrorDiv = true; } }); if(this.isShowErrorDiv) { this.errorMessageList.push('These required fields must be completed: ' + invalidFieldLabel.join(',')); } } reportValidityForField(fieldName,errorMessage) { console.log('fieldname : ' + fieldName); if(fieldName === 'Name') { this.template.querySelector('.accountName').setCustomValidity(errorMessage); this.template.querySelector('.accountName').reportValidity(); } else if(fieldName === 'AnnualRevenue') { this.template.querySelector('.accountRevenue').setCustomValidity(errorMessage); this.template.querySelector('.accountRevenue').reportValidity(); } } handleReset(event) { const inputFields = this.template.querySelectorAll( 'lightning-input-field' ); if (inputFields) { inputFields.forEach(field => { field.reset(); }); } } }
展示效果:
二. 「`」 的使用
我们在程序中应该很习惯的使用 track / api这种 reactive的变量,改动以后就可以走 rendercallback 然后前端UI会自动渲染和他关联的。除了使用这两个情况,还可以使用getter方式进行 field reactive操作。官方的描述为,如果字段声明不需要使用 track / api这种reactive变量,尽量不用,所以某些case下,我们可以使用 关键字 ``进行操作。这个标签是键盘的哪个呢,看下图?
看一下官方提供的demo
helloExpressions.html:输入框展示两个入力项,下面展示一个拼以后的大写。
<template> <lightning-card title="HelloExpressions" icon-name="custom:custom14"> <div class="slds-m-around_medium"> <lightning-input name="firstName" label="First Name" onchange={handleChange} ></lightning-input> <lightning-input name="lastName" label="Last Name" onchange={handleChange} ></lightning-input> <p class="slds-m-top_medium"> Uppercased Full Name: {uppercasedFullName} </p> </div> </lightning-card> </template>
helloExpressions.js:使用 `方式整合两个private的字段,实现reactive的效果。这里需要注意的是,如果使用 `以后必须要使用 ${}将变量套起来,这个是固定的写法。
import { LightningElement } from 'lwc'; export default class HelloExpressions extends LightningElement { firstName = ''; lastName = ''; handleChange(event) { const field = event.target.name; if (field === 'firstName') { this.firstName = event.target.value; } else if (field === 'lastName') { this.lastName = event.target.value; } } get uppercasedFullName() { return `${this.firstName} ${this.lastName}`.trim().toUpperCase(); } }
效果:
总结:篇中主要总结两点。1是 record-edit-form submit前的onclick使用;2是` 搭配 {}实现 reactive的效果。篇中有错误地方欢迎指出,有不懂的欢迎留言。
作者:zero
博客地址:http://www.cnblogs.com/zero-zyq/
本文欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接
如果文章的内容对你有帮助,欢迎点赞~
为方便手机端查看博客,现正在将博客迁移至微信公众号:Salesforce零基础学习,欢迎各位关注。