一个iframe如何获取其父元素的背景颜色?

3
我有一个在iframe中显示的Pardot(Salesforce)表单,并且可以控制两个域上的标记和脚本。该表单具有透明背景,有时父页面的背景照片或颜色与表单标签的文本颜色对比不足。当它是暗色文本在暗色背景上时,你无法读取First Name
我的目标是在iframe内设置一个body类,根据包含框架的父元素的颜色采样为.light-bg.dark-bg
在此代码中,iframe将能够确定div.framed-lead-form是否具有浅色或深色背景。有JS插件可获取元素的颜色饱和度(这个插件有有趣的许可证https://gist.github.com/larryfox/1636338),但我找不到任何可以通过iframes工作的东西。
<div class="framed-lead-form">
    <iframe src="//go.pardot.com/id" allowtransparency="true"></iframe>
</div>

1
可以使用postMessage API在两个窗口之间进行通信,或者在iframe中设置document.domain以匹配外部窗口,并通过此方式使用脚本访问iframe。 - charlietfl
5个回答

3

我做了一个主文档和iframe的小示例。
从主文档通过window post message发送主题信息
在iframe中监听并设置背景主题颜色

主文档: https://jsfiddle.net/kristapsv/L1fd64b3/33/

(function($){

$.fn.lightOrDark = function(){
var r,b,g,hsp
  , a = this.css('background-color');

if (a.match(/^rgb/)) {
  a = a.match(/^rgba?\((\d+),\s*(\d+),\s*(\d+)(?:,\s*(\d+(?:\.\d+)?))?\)$/);
  r = a[1];
  b = a[2];
  g = a[3];
} else {
  a = +("0x" + a.slice(1).replace( // thanks to jed : http://gist.github.com/983661
      a.length < 5 && /./g, '$&$&'
    )
  );
  r = a >> 16;
  b = a >> 8 & 255;
  g = a & 255;
}
hsp = Math.sqrt( // HSP equation from http://alienryderflex.com/hsp.html
  0.299 * (r * r) +
  0.587 * (g * g) +
  0.114 * (b * b)
);
if (hsp>127.5) {
  return 'light';
} else {
  return 'dark';
}
}

})(jQuery);

var iframe = document.getElementById('my-iframe');

// Set here light/dark depending on container or whatever color
var theme =  $('.container').lightOrDark();

var jsonMessage = {
  'action' : 'set-theme',
  'theme' : theme
};

iframe.contentWindow.postMessage(JSON.stringify(jsonMessage), '*');

Iframe: https://jsfiddle.net/kristapsv/zLL9db1c/11/

var messageHandler = function (event) {
  var message;

  try {
    message = JSON.parse(event.data);
  } catch (e) {
    return;
  }

  switch (message.action) {
    case 'set-theme':
        setTheme(message.theme);
        break;
  }
};

var setTheme = function(theme) {
  $('.text-container')
    .removeClass('dark')
    .removeClass('light')
    .addClass(theme);
}

window.addEventListener('message', messageHandler, false);

使用 https://gist.github.com/larryfox/1636338 更新,添加了可用的主题颜色检查。 - Kristapsv
巧妙地使用了框架小提琴!那是一个强大的演示。 - Dylan Valade

2

1
如果您可以控制iframe的src,您可以将其作为参数包含在内。
<div class="framed-lead-form">
    <iframe src="//go.pardot.com/id?bg=FF0000"></iframe>
</div>

你可能需要通过JavaScript在父文档中动态获取此颜色,但思路是相同的。你可以在DOM加载时完成此操作。Jquery示例:
$(function() {
    var bgColor = getPageBgColor();
    $('#my-frame').attr('src', '//go.pardot.com/id?bg=' + bgColor);
});

谢谢,这是一个更简单的方法,但我需要一些不需要人们了解十六进制颜色或GET参数的东西。用户将在任何地方粘贴样板表单代码,因此它必须自动知道其背景。 - Dylan Valade
明白了。看起来postMessage解决方案对于你的用户来说太过复杂了。我会为用户提供一个iframe和一个script标签的HTML代码。该脚本将更新iframe参数或执行postMessage操作。这仍然只需要一次复制和粘贴操作,但HTML代码更加复杂。 - Jimmie Tyrrell

0
我还没有测试过,但应该可以从 iframe 内部获取背景颜色。
window.parent.document.getElementById('framed-lead-form').style.backgroundColor

0

这应该可以工作

window.parent.document.getElementsByTagName("body")[0].style.backgroundColor;

只有在整个父页面使用相同的背景颜色时,这才有所帮助。这里的目标是了解 iframe 包含的父元素的颜色是什么。 - Dylan Valade

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接