如何控制iframe中主体元素的背景图像和颜色?注意,嵌入的body元素有一个类,iframe是属于我的站点的一个页面。

我需要这个的原因是,我的网站有一个黑色背景分配给主体,然后一个白色背景分配给包含文本的div。所见即所得编辑器在编辑时使用iframe来嵌入内容,但它不包括div,因此文本很难阅读。

iframe的主体在编辑器中有一个在其他任何地方都不使用的类,所以我假设这个放在那里是为了解决这样的问题。然而,当我将样式应用到类时。它们不会覆盖应用于Body的样式。奇怪的是,样式确实出现在Firebug中,所以我不知道发生了什么!

谢谢

更新-我已经尝试了@mikeq的解决方案,添加一个样式的类,是身体的类。这在添加到主页的样式表时不起作用,但在添加到Firebug时起作用。我假设这是因为Firebug应用于页面上的所有元素,而CSS没有应用于iframes中。这是否意味着添加css后窗口加载与JavaScript将工作?


当前回答

如果你控制了承载iframe的页面和iframe的页面,你可以将一个查询参数传递给iframe…

下面是一个根据托管站点是否为移动站点向iframe添加类的示例…

添加内嵌框架:

var isMobile=$("mobile").length; //detect if page is mobile
var iFrameUrl ="https://myiframesite/?isMobile=" + isMobile; 

$(body).append("<div id='wrapper'><iframe src=''></iframe></div>");
$("#wrapper iframe").attr("src", iFrameUrl ); 

iFrame内:

//add mobile class if needed
var url = new URL(window.location.href);
var isMobile = url.searchParams.get("isMobile");
if(isMobile == "1") {
    $("body").addClass("mobile");
}

其他回答

覆盖另一个域iframe CSS

通过使用SimpleSam5的部分答案,我通过一些Tawk的聊天iframe实现了这一点(他们的定制界面很好,但我需要进一步的定制)。

在移动设备上显示的这个iframe中,我需要隐藏默认图标,并放置一个背景图像。我做了以下事情:

Tawk_API.onLoad = function() {
// without a specific API, you may try a similar load function
// perhaps with a setTimeout to ensure the iframe's content is fully loaded
  $('#mtawkchat-minified-iframe-element').
    contents().find("head").append(
     $("<style type='text/css'>"+
       "#tawkchat-status-text-container {"+
         "background: url(https://example.net/img/my_mobile_bg.png) no-repeat center center blue;"+
         "background-size: 100%;"+
       "} "+
       "#tawkchat-status-icon {display:none} </style>")
   );
};

我不拥有任何Tawk的域名,这对我来说是有用的,因此你可以这样做,即使它不是来自同一个父域(尽管Jeremy Becker对Sam的回答发表了评论)。

如果你控制了承载iframe的页面和iframe的页面,你可以将一个查询参数传递给iframe…

下面是一个根据托管站点是否为移动站点向iframe添加类的示例…

添加内嵌框架:

var isMobile=$("mobile").length; //detect if page is mobile
var iFrameUrl ="https://myiframesite/?isMobile=" + isMobile; 

$(body).append("<div id='wrapper'><iframe src=''></iframe></div>");
$("#wrapper iframe").attr("src", iFrameUrl ); 

iFrame内:

//add mobile class if needed
var url = new URL(window.location.href);
var isMobile = url.searchParams.get("isMobile");
if(isMobile == "1") {
    $("body").addClass("mobile");
}

对于一个iframe,你可以这样做:

document.querySelector('iframe').contentDocument.body.style.backgroundColor = '#1e1e2d';

如果你有多个iframe,你正在处理:

document.querySelectorAll('iframe').forEach((iframe) => {
    iframe.contentDocument.body.style.backgroundColor = '#1e1e2d';
});

这应该与跨域工作,如果你是两者的所有者

这里的技巧是为你的主体分配一个全局css变量,用新颜色监听消息,然后在收到消息后更改全局css变量。

我使用角,但它应该与纯javascript工作

我的用例是在保存之前向用户展示颜色变化如何影响他在iframe中的网站

域一个

@ViewChildren('iframeContainer') iframeContainer: QueryList<ElementRef>

sendDataToIframe(
  data = {
      type: 'colorChange',
      colors: {primary: '#000', secondary: '#fff'},
  },
): void {
  if (this.targetUrl)
    this.iframeContainer.first.nativeElement.contentWindow.postMessage(data) // You may use document.getElementById('iframeContainer') instead
}

域B

acceptedEditOrigins = [
  'https://my.origine.ccom', // Be sur to have a correct origin, to avoid xss injecto: https://en.wikipedia.org/wiki/Cross-site_scripting
]

constructor() {
// Listen to message
window.addEventListener('message', (event) => this.receiveMessage(event), false)
}

receiveMessage(event: MessageEvent) {
  if (this.acceptedEditOrigins.includes(event.origin))
    switch (event.data.type) {
      case 'colorChange': {
        this.setWebsiteConfigColor(event.data.colors)
      }
    }
}

setWebsiteConfigColor(colors: WebsiteConfigColors) {
  if (colors) {
    const root = document.documentElement
    for (const [key, value] of Object.entries(colors)) {
       root.style.setProperty(`--${key}`, value) // --primary: #000, --secondary: #fff
    }
  }
}

body {
  background-color: var(--primary);
}

给你的iframe页面的主体一个ID(或者类,如果你愿意)

<html>
<head></head>
<body id="myId">
</body>
</html>

然后,同样在iframe的页面中,在CSS中为它分配一个背景

#myId {
    background-color: white;
}