0

I've been trying to get this related list to render on a lightning web component, and when it updates the only thing that doesn't work is the on click listeners... sort of.

Here's the relevant LWC JS

    @api recordData;
    @api callLogList = [];
    @track selectedLog;

    @track showAllCallLogs = false;
    @track callChainRecordReference;
    @track recordError;
    @track isLoading = true;
    @track multipleCallLogs = false;

    connectedCallback() {
        this.setup();

        this.callChainRecordReference = {
            type: 'standard__recordPage',
            attributes: {
                recordId: this.recordData.Id,
                objectApiName: 'Call_Log_Chain__c',
                actionName: 'view'
            },
        };
    }

    renderedCallback() {
        if(!this.callLogList[0].setSelected){
            this.setup();
        }
    }

    setup(){
        let callHistory = [];

        console.log(JSON.parse(JSON.stringify(this.callLogList)));
        this.callLogList.forEach(log => {
            // Clone the object and set the setSelected function up for each log
            let tempLog = {...log,
                isSelected: false,
                isResolved: log.Status__c === 'Resolved',
                setSelected: () => {
                    let callLogTempList = [];
                    this.callLogList.forEach(callLog => {
                        if(log.Id === callLog.Id){
                            callLogTempList.push({...callLog, isSelected: true});
                            this.selectedLog = callLog;
                        } else {
                            callLogTempList.push({...callLog, isSelected: false});
                        }
                    });
                    this.callLogList = callLogTempList;
                }};
            if(tempLog.isResolved && !this.isResolved){
                let tempRec = {...this.recordData}
                tempRec.Status__c = "Resolved";
                this.recordData = tempRec;
            }
            callHistory.push(tempLog);
        });

        callHistory.sort((date1, date2) => {
            return new Date(date1.LastModifiedDate) - new Date(date2.LastModifiedDate);
        });

        this.callLogList = callHistory;

        // Select the last log in the list
        this.callLogList[this.callLogList.length - 1].isSelected = true;
        this.selectedLog = this.callLogList[this.callLogList.length - 1];

        if(this.callLogList.length > 1){
            this.multipleCallLogs = true;
        }
    }

And here's the corresponding HTML template

<!-- Member Call Log Chain Card -->
<template>
    <div class="slds-card slds-card_boundary">
        <div class="slds-card__header slds-grid slds-m-bottom_small">
            <header class="slds-media slds-media_center slds-has-flexi-truncate">
                <div class="slds-media__body">
                    <h2 class="slds-card__header-title">
                        <span onclick={goToCallChainPage} style="cursor:pointer;color: #0000EE;text-decoration: underline">{Name}</span>
                    </h2>
                </div>
                <template if:true={multipleCallLogs}>
                    <template if:true={showAllCallLogs}>
                        <div class="slds-no-flex">
                            <button class="slds-button slds-button_neutral" onclick={showAllCallLogDetails}>Show Selected</button>
                        </div>
                    </template>
                    <template if:false={showAllCallLogs}>
                        <div class="slds-no-flex">
                            <button class="slds-button slds-button_neutral" onclick={showAllCallLogDetails}>Show All</button>
                        </div>
                    </template>
                </template>
            </header>
        </div>

        <div class="slds-card__body slds-card__body_inner">
            <div class="slds-grid slds-grid_align-spread slds-m-bottom_small slds-p-bottom_small slds-border_bottom">
                <div class="slds-col">
                    <template iterator:it={callLogList}>
                        <span key={it.value.Id}>
                            <template if:true={it.value.isSelected}>
                                <lightning-badge label={it.value.Name} class="slds-badge_inverse slds-m-bottom_x-small" style="cursor:pointer" onclick={it.value.setSelected}></lightning-badge>
                            </template>
                            <template if:false={it.value.isSelected}>
                                <lightning-badge label={it.value.Name} class="slds-m-bottom_x-small" style="cursor:pointer" onclick={it.value.setSelected}></lightning-badge>
                            </template>
                            <template if:false={it.last}>
                                <lightning-icon class="slds-m-horizontal_x-small" icon-name="utility:forward" size="x-small"></lightning-icon>
                            </template>
                            <template if:true={it.last}>
                                <template if:false={isResolved}>
                                    <lightning-icon class="slds-m-horizontal_x-small" icon-name="utility:forward" size="x-small"></lightning-icon>
                                    <lightning-badge class="slds-badge_lightest slds-m-bottom_x-small" label="Add to Chain" icon-name="utility:add" style="cursor:pointer" onclick={addToCallChain}></lightning-badge>
                                </template>
                            </template>
                        </span>
                    </template>
                </div>

                <template if:false={isResolved}>
                    <template if:true={isOverdue}>
                        <div class="slds-col">
                            <lightning-badge label={Status} class="slds-theme_error"></lightning-badge>
                        </div>
                    </template>
                    <template if:false={isOverdue}>
                        <div class="slds-col">
                            <lightning-badge label={Status} class="slds-theme_warning"></lightning-badge>
                        </div>
                    </template>
                </template>
                <template if:true={isResolved}>
                    <div class="slds-col">
                        <lightning-badge label={Status} class="slds-theme_success"></lightning-badge>
                    </div>
                </template>
            </div>

            <div class="slds-col">
                <template if:true={showAllCallLogs}>
                    <template for:each={callLogList} for:item="log">
                        <div key={log.Id} class="slds-border_bottom">
                            <c-member_-call-log-card record-data={log}></c-member_-call-log-card>
                        </div>
                    </template>
                </template>
                <template if:false={showAllCallLogs}>
                    <c-member_-call-log-card record-data={selectedLog}></c-member_-call-log-card>
                </template>
            </div>
        </div>
        <template if:true={recordError}>
            <div class="slds-align_absolute-center slds-text-align_center">
                <c-white-glove_-caller-auth-warning-message
                        warning-header="Error getting Call Log"
                        warning-message={recordError}>
                </c-white-glove_-caller-auth-warning-message>
            </div>
        </template>
    </div>
</template>

At a high level, I just have a function that loops through the Id's and sets the displayed card up. That function gets set on the object itself when the list is passed in from the parent component. (Connected Callback -> this.setup). I'm doing it this way because I can't just pass an ID to the 'setSelected' function onClick since LWC doesn't support parameters in the template. On the initial render, everything works fine. But when I update the list by passing a new one from the parent the only click listener getting set is the last one in the list. I'm crazy lost because it's the exact same code being run from connected to rendered and only connected gives me what I want.

Is there something I'm missing? I've been pouring over the docs and can't find anything that would explain this. Do the click listeners only get set once per connection and then silently fail?

chinnc
  • 106
  • 7

0 Answers0