You need to sign in to do that
Don't have an account?
rubixtious
Using Record Types with Visualforce Pages
We have overidden our new and edit buttons for Cases to go to a custom visualforce page. This was fine until now we want to utilize Record Types. Now, regardless of the record type chosen, new cases go to the custom visualforce page instead of the page layout for the record type. I am thinking that I need another VF page to act as a proxy to route the user to the correct page. I have read a couple of forum posts but am unsure if they are applicable to my problem.
http://forums.sforce.com/sforce/board/message?board.id=Visualforce&thread.id=4875
'/(keyprefix)/e?nooverride=1&RecordType={!$Request.RecordType}'
so that you can redirect to Standard New pages and it will take the selected RecordType.
This URL is called after Record Type selection, and selected RecordType is put in RecordType parameter (because you don't use URLFOR anymore, you have to put all parameters by yourself). The parameter nooverride=1 does the same thing as URLFOR(Action..., null, null, true) so that you can call original New page. You just add your field id & value pairs and other parameters (retURL, cancelURL, etc.) in the URL.
In my case, I put the routing logic in an action method (redirect()) and let it return PageReference for '/(keyprefix)/e?nooverride=1&RecordType={!$Request.RecordType}' based on given parameters.You can do the same thing with javascript document.location.
When I inherited "save_new" parameter, it still showed RecordType Selection page twice.
I hope this can help you (it worked perfect in my case).
ThomasTT
<apex:page standardController="Opportunity" extensions="OpportunityRedirectExtension" action="{!redirect}">
</apex:page>
public with sharing class OpportunityRedirectExtension {
private ApexPages.StandardController controller = null;
public OpportunityRedirectExtension (ApexPages.StandardController controller){
this.controller = controller;
}
public PageReference redirect(){
String prefix = Opportunity.SObjectType.getDescribe().getKeyPrefix();
String param = getParameters() + '&(your field id)=(your field value)';
return new PageReference('/'+prefix+'/e?nooverride=1&'+param);
}
// Inherit previous parameters, more imporatntly, RecordType parameter!
private String getParameters(){
string param = '';
Map<String, String> strMap = ApexPages.currentPage().getParameters();
String[] keys = new String[]{'RecordType', 'retURL', 'cancelURL'};
for(String s : keys){
if(strMap.containsKey(S)) param += s + '=' + strMap.get(s) + '&';
}
if(param.length() > 0) param = param.substring(0, param.length()-1);
return param;
}
}
All Answers
Here's an example of a simple VF page that acts as a proxy/redirector which can be set of the overriden "New" page:
<apex:page standardController="DemoObject__c" extensions="NewDemoObjDispatcher" action="{!redirectToPage}">
</apex:page>
Then here is the supported controller extension:
Make sense?
Hi Ryan,
I have some of this working using a variation of the code you posted. My problem now is redirecting to the standard new page for a particular record type. I am not sure what to return to get to the standard controller. If I return null, the redirect works but only after returning to the record types screen first. So essentially the user is asked to choose the record type twice. The redirect to the custom VF page is working fine. Thanks for your help.
public class ControllerDispatcherNewCase { public ControllerDispatcherNewCase(ApexPages.StandardController controller) { this.controller = controller; } public PageReference getRedir() { Pagereference newPage; if(Apexpages.currentPage().getParameters().get('RecordType') == '012R00000000Mu1') { // Case Standard Page return null; } else if(Apexpages.currentPage().getParameters().get('RecordType') == '012R00000000Mu6') { newPage = Page.editCase; // Case VF Page return newPage.setRedirect(true); } else { return null; } } private final ApexPages.StandardController controller; }
<apex:page standardController="Case" extensions="ControllerDispatcherNewCase" action="{!nullValue(redir.url, urlFor($Action.Case.NewCase, null, null, true))}"> </apex:page>
Yes, thats right.
RecordType 1 should go to custom VF page
RecordType 2 should go to standard 'new' case page for that record type
RecordType1 works fine and redirects to the custom VF page
RecordType2 redirects to the 'select record type' screen twice and only then redirects to the standard 'new' case page.
'/(keyprefix)/e?nooverride=1&RecordType={!$Request.RecordType}'
so that you can redirect to Standard New pages and it will take the selected RecordType.
This URL is called after Record Type selection, and selected RecordType is put in RecordType parameter (because you don't use URLFOR anymore, you have to put all parameters by yourself). The parameter nooverride=1 does the same thing as URLFOR(Action..., null, null, true) so that you can call original New page. You just add your field id & value pairs and other parameters (retURL, cancelURL, etc.) in the URL.
In my case, I put the routing logic in an action method (redirect()) and let it return PageReference for '/(keyprefix)/e?nooverride=1&RecordType={!$Request.RecordType}' based on given parameters.You can do the same thing with javascript document.location.
When I inherited "save_new" parameter, it still showed RecordType Selection page twice.
I hope this can help you (it worked perfect in my case).
ThomasTT
<apex:page standardController="Opportunity" extensions="OpportunityRedirectExtension" action="{!redirect}">
</apex:page>
public with sharing class OpportunityRedirectExtension {
private ApexPages.StandardController controller = null;
public OpportunityRedirectExtension (ApexPages.StandardController controller){
this.controller = controller;
}
public PageReference redirect(){
String prefix = Opportunity.SObjectType.getDescribe().getKeyPrefix();
String param = getParameters() + '&(your field id)=(your field value)';
return new PageReference('/'+prefix+'/e?nooverride=1&'+param);
}
// Inherit previous parameters, more imporatntly, RecordType parameter!
private String getParameters(){
string param = '';
Map<String, String> strMap = ApexPages.currentPage().getParameters();
String[] keys = new String[]{'RecordType', 'retURL', 'cancelURL'};
for(String s : keys){
if(strMap.containsKey(S)) param += s + '=' + strMap.get(s) + '&';
}
if(param.length() > 0) param = param.substring(0, param.length()-1);
return param;
}
}
Thanks Thomas! This seems to work but I am not sure I understand what/why I need to specify the field id and value pairs. I have removed that string and my page works as intended. Also, I have not specified a retURL or cancelURL, the defaults work fine.
> I have removed that string and my page works as intended.
You mean, you removed the following part?
...
return new PageReference('/'+prefix+'/e?nooverride=1&'+param);
...
Map<String, String> strMap = ApexPages.currentPage().getParameters();
String[] keys = new String[]{'RecordType', 'retURL', 'cancelURL'};
for(String s : keys){
if(strMap.containsKey(S)) param += s + '=' + strMap.get(s) + '&';
}
if(param.length() > 0) param = param.substring(0, param.length()-1);
return param;
...
In my case, if I just use "PageReference('/'+prefix+'/e?nooverride=1)", any parameter was not inherited from the original or RecordType selection page. In my actual code, I inherits all parameters except "save_new".
If they are automatically inherited without any adding parameters by yourself, that's fine... I don't know why it didn't work for me.
If there is no cancelURL in the URL at the final page, but still Cancel button is working, that may be just a coincidence... if you invoke that event and try to cancel the event, it may not lead you back to the original page.
One additional note on this... If the parameter value contains unsafe characters such as & or #, the page may not be redirected with all the parameters specified. Example, if the paramter value is an account name of 'Detroit Auto & Bicycle', the '&' character causes issues.
To correct this, you can use the EncodingUtil.UrlEncode function, such as below...
Ben0034,
That is very true. I always forget about encoding...
ThomasTT
How to get the exact parameters? I mean, in strMap we have the exact parameters. But in param we have only 'RecordType', 'retURL', 'cancelURL'.
Here is some code I ended up with to solved a related problem:
Automatically setting the record type of a detail object based on the record type of its master object
This is great, and it works well if a particular profile has multiple RecordTypes available to it, but it turns out that it does NOT seem to work if you have a profile with only one accessible record type -- in that case the record type doesn't seem to be on the query string.
I'm at this point to figure out the best way to determine what the default record type is for the profile in this situation, because then I could determine what record type is being selected -- and then follow the same logic to determine if I go to the standard new page layout, or my custom VisualForce page.
You could possibly use Describe methods as follows:
Schema.DescribeSObjectResult R = Account.SObjectType.getDescribe(); List<Schema.RecordTypeInfo> RT = R.getRecordTypeInfos();
if(rt.isDefaultRecordTypeMapping())
//do something
Can someone post this same exact code, but with the actual object values that they are using? I am trying to accomplish same exact thing here, but I am not a developer, and don't know exactly what I need to add to make this work.
Thanks!
Hi ThomasTT,
I´m trying to do exactly what you are doing with opportunities, but mi point is to open a visualforce page for Edit a certain kind of record Type.
When I try to use your code i´m redirecting to the Standart salesforce Record type and I cannot manage to redirect the user to a page called IPOpp_New for that record type.
I would really apreciate some help with this, its a mayor issue for my developing.
Thanks from the heart for your help!
Best regards,