Disabling Custom CSS (added in the Forms 2.0 Editor) on a per-page basis

A client had a conundrum.

They are — as we firmly recommend— using a global Marketo contact form across many pages.

But the form has built-in Custom CSS (Form Settings » Form Theme » » Edit Custom CSS in Form Editor). That CSS was built to match the look-and-feel of older pages. But their new LPs have a dark theme, different fonts, and a different layout, so the CSS made an ugly contrast.

For a visual hint, imagine this CSS:

Which is gonna make the form look like this:

Even if you want it like this:

Those !importants will be maddening to override in an additional stylesheet, and there could of course be hundreds of different rules. It’s practically impossible to have full-featured Custom CSS stored in the form descriptor and also override it.

What to do?

The simplest answer, of course, is stop using the built-in Custom CSS feature. Indeed, if you can move the CSS to an external stylesheet, you can conditionally include the <link rel="stylesheet"> per-page.

But that’s a very big “if”. In this case, it was impossible. There were countless pages, including pages on external sites that couldn’t be touched, relying on the Custom CSS. It just needed to be turned off for some new pages.

Custom CSS becomes an anonymous style

When a form descriptor is loaded from Marketo, the contents of the Custom CSS box are injected at the base of the <head>, in a dedicated inline <style>:

That means if you merely mark up the Custom CSS with a @namespace rule, as described in my last blog post...

... you can find the stylesheet and disable it where needed:

MktoForms2.whenReady(function(mktoForm){
   getStyleSheetsByPrefix("mktoFormDescriptorCustomCSS").forEach(function(ss){
     ss.disabled = true;
   });
});

Setting a stylesheet to disabled is amazing. No need to worry about !important or selector specificity: the styles are just powered off. Done!

There’s still one concern, though. If you peer closely at the GIF below (recorded at 30fps) you can see the original styles are still present for a fraction of a second before being disabled:

To take care of that, hide all Marketo forms by default (this would itself go in a local <style> tag, above the form embed):

.mktoForm {
   visibility: hidden;
   position: absolute;
}
.mktoForm[data-descriptor-custom-css-removed="true"] {
   visibility: visible;
   position: static;
}

And then immediately after disabling the offending <style>, show the form:

MktoForms2.whenReady(function(mktoForm){
   getStyleSheetsByPrefix("mktoFormDescriptorCustomCSS").forEach(function(ss){
     ss.disabled = true;
   });
   
   let formEl = mktoForm.getFormElem()[0];   
   formEl.setAttribute("data-descriptor-custom-css-removed","true");
});

Still, if you do have a choice going forward, use remote <link>’d stylesheets instead of built-in Custom CSS. Future you will thank you.