function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
SamarthyaSamarthya 

apex:component + Ajax + Submit.

Just a curious question - I had asked it before but did not get right answer.

 

1. I have defined a component with one text field / input field.

2. I have a submit button at the bottom of the outputPanel.

3. When I press submit button the value from text box is passed on to the Class object with corresponding getter being called.

4. When I introduce a new button and call some AJAX based function the object is never set.

 

 

What is the thing that I am missing?

Is it that component will call the corresponding setter only after submit is called (POST).

 

- Samarthya

bob_buzzardbob_buzzard

How are you making the ajax call?  Are you using an actionFunction?  If so, the form should be submitted back in the same way as when clicking a command button.

 

SamarthyaSamarthya

Yes I am using action button Ajax call runs fine I populated some string with the results of the call and when I push that information to screen it shows. The only problem I have is the component based object setter is not getting called with the values in the text fields for the object variable defined.

SamarthyaSamarthya

Action function I meant. I call a javascript and from java script I make a call to the action function. It runs fine.

bob_buzzardbob_buzzard

Is your actionfunction rerendering a section of the page?  There's been a problem around for a while now when submitting values back via apex:param tags and with actionfunctions that don't rerender.  I'm wondering if you are experiencing something similar.

SamarthyaSamarthya

No th re-rendering is working fine. May be I am not able to explain it properly. Let me try again (BTW thank you for your kind patience)

 

1. I am using this to make an AJAX call

<apex:outputPanel id="testAjax" onclick="callWS()" styleClass="btn"> Make It 
</apex:outputPanel>

 This call does not calls the setter for the object for which a component has been defined.

 

End result I make the AJAX call with dummy parameters perfectly, but the object which I intend to fill in with values from the component (on the same page) fails as there is no submit. 

 

So my question is - Is there a way around it? or I am doing something wrong.

 

<c:InformationForm id="FormInfo" Address="{!objFill}"/>

 

 

I use the above component on the same page to get the values in the objFill.

 

 

- Samarthya

 

 

bob_buzzardbob_buzzard

It doesn't sound like you are doing anything wrong, I've used actionfunctions to submit changes via onclick events in the past without issue.  Its difficult to understand exactly what you are doing from snippets - is it possible to post your code, or is there too much of it?

SamarthyaSamarthya

The controller code for the page is 

 

public class TestpageController
{
    public Address address
    {
        get;
        set;
    }
    
    public PageReference submit()
    {
        if(address != null)
            address.street = 'not null';
        return null;
    }
    
    public PageReference reload()
    {
        return null;
    }
    
    public String strData
    {
        get;
        set;
    }
    
    private void convertToString()
    {
        strData = address.street + ' ' + address.country + ' ' +address.pincode;
    }
    
    public void callWSAJAX()
    {
        if((address == null) || (address.street == null) || (address.street.length() == 0))
        {
            address = new Address();
            address.street='new address';
            address.country='wonderland';
        }
        
        convertToString();
    }
}

 

 

I call callWSAJAX() from the action function on the outputPanel click.

 

The component is 

 

<apex:component >
    <apex:attribute name="Address" type="Address"/>
        <div>
        <label for="AddressValue">{!$Label.Street}</label>
        <apex:inputText id="AddressValue" tabindex="1" styleClass="inputField"  value="{!Address.street}"/>
        <!-- ensure focus to this element after loading -->
        <script type="text/javascript">$(escId('{!$Component.AddressValue}')).focus();</script>
    </div>
    
    <div>
        <label for="Country" >{!$Label.Country}</label>
        <apex:inputText id="Country" tabindex="2" styleClass="inputField"  value="{!Address.country}"/>
    </div>
    
    <div >
        <label for="PinCode" >{!$Label.Pincode}</label>
        <apex:inputText id="PinCode" tabindex="3" styleClass="inputField"  value="{!Address.pincode}"/>
    </div>       
    
</apex:component>

 

 

 

 

SamarthyaSamarthya

The Address class is simply

 

public class Address
{
    public String street {
    get;
    set;
    }
    public String country
    {
    get;
    set;
    }
    public String pincode
    {
    get;
    set;
    }
}

 

 

and the test page is

 

 

<apex:page sidebar="false" showHeader="false" id="TestPage" controller="TestpageController">
    <head>
        <script type="text/javascript">
            function callWS(str)
            {    
                alert(str);
                callAFWS();
            }
        </script>
    </head>

        <apex:define name="page_content">
           <div id="AddressInputPanel">
              <apex:form id="addressForm">                  
                    
                    <apex:actionFunction id="callAFWS" immediate="true" name="callAFWS" action="{!callWSAJAX}" reRender="dataRecvd" status="statusWS">                                                                                 
                    </apex:actionFunction>
                    <c:AddressInput id="AddressInput" Address="{!address}"/>
                    <div id="AddressForm" class="addressForm" style="width:50%; margin-left: 00px;">
                        <h4>Address Input Panel</h4>
                        <div class="vmiddleContent">
                            <apex:commandButton id="AnalyzeAddress" value="Check" tabindex="100" action="{!submit}" styleClass="button" status="actionStatus" reRender="addressForm"/>
                            <apex:actionStatus id="actionStatus" startStyleClass="StatusPanel" stopStyleClass="StatusPanel" onstop="scrollIntoView('ActionSection');">
                                <apex:facet name="start">
                                    <apex:image id="actionStatusImg" styleClass="ajaxSpinner" alt="" title="Loading"/>
                                </apex:facet>
                            </apex:actionStatus>
                            <apex:outputPanel id="testAjax" onclick="callWS()" styleClass="btn"> Get Candidates 
                                <apex:param id="str1" value="{!address}"/>
                            </apex:outputPanel>
                        </div>

                        <apex:outputpanel id="dataRecvd" styleClass="error">                            
                            <apex:actionStatus id="statusWS">
                            <apex:facet name="stop">Text {!strData} </apex:facet>                            
                            </apex:actionStatus>
                        </apex:outputpanel>

                    </div>
                    
                </apex:form>
            </div>
        </apex:define>      

</apex:page>

 

 

 

bob_buzzardbob_buzzard
You have a rerender in your actionfunction which means that your component won't be redrawn.  Once the action function has completed, only the dataRecvd panel will be redrawn.
                  <apex:actionFunction id="callAFWS" immediate="true" name="callAFWS" action="{!callWSAJAX}" reRender="dataRecvd" status="statusWS">                                                                                 
                    </apex:actionFunction>

...
                        <apex:outputpanel id="dataRecvd" styleClass="error">                            
                            <apex:actionStatus id="statusWS">
                            <apex:facet name="stop">Text {!strData} </apex:facet>                            
                            </apex:actionStatus>
                        </apex:outputpanel>

                    </div>
                    
                </apex:form>
            </div>
        </apex:define>      

</apex:page>

 

SamarthyaSamarthya

If I re-render the complete form will the values be pushed into the component (object)?

SamarthyaSamarthya

I am just speculating (as I did not read it in any documentation) that without actually submitting the data (HTTP POST) the component based object will not receive the values (Setter wont be called). 

 

When I actually replace it with a command LINK or Button - the component recieves the value, but then there is no point in calling AJAX.

 

- Samarthya

bob_buzzardbob_buzzard

An actionfunction will cause an HTTP post to happen for the form.  Then if you re-render the component, it should pick up the latest values.