1

I have a custom object that has a Master-Detail relationship to the Opportunity object. I created a Visualforce page that I want to use to override the standard "New" list button on the related list of the custom object on the Opportunity. However, I want to be able to pass through the Opportunity ID and the Owner ID to the newly created page, as there are some variables that are formula lookups to fields on the Opportunity and Account. Does anyone know how I can do this? In the past I've used a URL hack to create the button, but I understand those will be going away soon, so I would like a more scalable way to do this. Thanks!

VF Page:

<apex:page standardController="Opportunity" tabStyle="Opportunity" extensions="VF_SFController" action="{!SF}">

<apex:form >

    <apex:repeat value="{!ESF}" var="SF">

    Contact Information
        <Table columns="5" width="100%">
            <tr>
                <td width="10%">Name:</td>
                <td width="38%"><apex:outputField value="{!SF.Rep__c}"/></td>
                <td width="4%">&nbsp;</td>
                <td width="10%">Amount:</td>
                <td width="38%"><apex:outputField value="{!SF.Amount__c}"/></td><p class="double"></p>
            </tr>
            <tr>
                <td width="10%">Phone:</td>
                <td width="38%"><apex:outputField value="{!SF.Sales_Rep_Phone__c}"/></td>
                <td width="4%">&nbsp;</td>
                <td width="10%">Opportunity:</td>
                <td width="38%"><apex:outputField value="{!SF.Opportunity__c}"/></td><p class="double"></p>
            </tr>
            <tr>
                <td width="10%">Email:</td>
                <td width="38%"><apex:outputField value="{!SF.Sales_Rep_Email__c}"/></td>
                <td width="4%">&nbsp;</td>
                <td width="10%">Account:</td>
                <td width="38%"><apex:outputField value="{!SF.Legal_Name__c}"/></td><p class="double"></p>
            </tr>
        </Table>

    </apex:repeat>
</apex:form>
</apex:page>

Custom Controller:

public class VF_SFController{

public List<SF__c> ESF {get; set;}

    private final Opportunity opp;
    public VF_SFController(ApexPages.StandardController myController){
        SF = new List<SF__c>();
        opp=(Opportunity)myController.getrecord();
    }

    public SF__c SF2 = new SF__c();
        public void SF(){

            SF2.Opportunity__c = opp.Id;
            SF2.Rep__c = opp.OwnerId;
            SF2.Amount__c = opp.Amount;
            SF.add(SF2);
        }

    public PageReference save() {

        PageReference RetPage = new PageReference('/apex/SFViewPage?id=' + SF[0].id);
        RetPage.setRedirect(true);
        return RetPage;
    }
}
8
  • just curious can you provide link that says URL redirect / URL hack will be going away soon?
    – Rao
    Nov 4, 2015 at 21:36
  • I haven't seen anything official, but I've seen a few comments about it and this site talks about it towards the end of the article: salesforceweek.ly/2015/08/struck-by-lightning.html
    – J. Neilan
    Nov 4, 2015 at 21:44
  • 1
    I feel the write up is very specific to what is in and out for lightning. PageReference.getParameters().put('id', myID); attaches the id param to the page url. Salesforce cannot offically stop supporting it unless they decide to depracte few existing features
    – Rao
    Nov 4, 2015 at 21:56
  • 1
    the getRecord() will include the Opportunity Id plus any merge fields on the VF page that are bound to the Opportunity object. If you don't include these, then you need to query for them in either the constructor or, through use of a page action method (that gets called after the constructor finishes)
    – cropredy
    Nov 5, 2015 at 6:48
  • 1
    One common misconception is that getRecord() works like trigger contexts and the entire Opportunity record is available to the controller. Not true. getRecord() only makes available to the controller the fields defined on the page of the form {!Opportunity.xxx} - these can be hidden fields -- or, you can use method addFields(). See doc on each method here: developer.salesforce.com/docs/atlas.en-us.pages.meta/pages/…
    – cropredy
    Nov 5, 2015 at 18:53

1 Answer 1

1

One common misconception is that getRecord() works like trigger contexts and the entire Opportunity record is available to the controller. Not true. getRecord() only makes available to the controller the fields defined on the page of the form e.g. {!Opportunity.xxx} - these can be hidden fields -- or, you can use method addFields().

here is the standard controller doc but I've excerpted the relevant bits:

getRecord()

Usage Note that only the fields that are referenced in the associated Visualforce markup are available for querying on this SObject. All other fields, including fields from any related objects, must be queried using a SOQL expression.

Tip

You can work around this restriction by including a hidden component that references any additional fields that you want to query. Hide the component from display by setting the component's rendered attribute to false.

addFields(...)

When a Visualforce page is loaded, the fields accessible to the page are based on the fields referenced in the Visualforce markup. This method adds a reference to each field specified in fieldNames so that the controller can explicitly access those fields as well.

Usage

This method should be called before a record has been loaded—typically, it's called by the controller's constructor. If this method is called outside of the constructor, you must use the reset() method before calling addFields().

The strings in fieldNames can either be the API name of a field, such as AccountId, or they can be explicit relationships to fields, such as foo__r.myField__c.

So it is up to you which way to go, for example with addFields you could do in your constructor...

myController.addFields(new List<String> {'ownerId','amount'});
opp=(Opportunity)myController.getrecord();

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .