Переопределить стиль тела для содержимого в iframe

165

Как я могу контролировать фоновое изображение и цвет элемента тела внутри iframe? Обратите внимание, что встроенный элемент body имеет класс и iframeявляется частью страницы, которая является частью моего сайта.

Причина, по которой мне это нужно, заключается в том, что моему сайту назначен черный фон для тела, а затем белый фон для элементов div, содержащих текст. Редактор WYSIWYG использует iframeдля встраивания контента при редактировании, но он не включает в себя div, поэтому текст очень трудно читать.

В теле iframeоператора when есть класс, который больше нигде не используется, поэтому я предполагаю, что он был помещен туда, чтобы такие проблемы могли быть решены. Однако, когда я применяю стили к ним, class.bodyони не переопределяют стили, применяемые к телу. Странно то, что стили появляются в Firebug, поэтому я понятия не имею, что происходит!

Спасибо

ОБНОВЛЕНИЕ - Я попробовал решение @ mikeq добавить стиль к классу, который является классом тела. Это не работает при добавлении в таблицу стилей главной страницы, но работает при добавлении с Firebug. Я предполагаю, что это потому, что Firebug применяется ко всем элементам на странице, тогда как CSS не применяется внутри фреймов. Означает ли это, что добавление CSS после загрузки окна с JavaScript будет работать?

jd6699
источник
1
Возможный дубликат Как применить CSS к iframe?
2540625
Несмотря на то, что в iframe невозможно что-либо коснуться, загрузка этого URL-адреса для каждого Ajax в <div>банку может быть временным решением (если это разрешено с помощью CORS-заголовка) ... (и «санация» загруженных данных с помощью регулярных выражений в кстати. Да все взломанные ...)
Фрэнк
Вы можете использовать javascript, если доменные страницы совпадают, но почему бы просто не поместить блок стиля в HTML вашей внутренней страницы, чтобы переопределить цвета, которые вы хотите изменить? Просто добавьте больше селекторов в ваше переопределение или используйте важные! если все остальное не удается, переопределить любые стили цвета, которые вы хотите, только на этой одной странице ...
О. Г. Шон

Ответы:

112

Iframe - это «дыра» на вашей странице, которая отображает другую веб-страницу внутри него. Содержимое iframe не имеет формы и не является частью вашей родительской страницы.

Как уже говорили другие, ваши варианты:

  • дать файлу, который загружается в iframe необходимый CSS
  • если файл в iframe находится в том же домене, что и ваш родитель, то вы можете получить доступ к DOM документа в iframe от родителя.
DA.
источник
251

Приведенное ниже работает только в том случае, если содержимое iframe принадлежит тому же родительскому домену.

Следующий скрипт jquery работает для меня. Протестировано на Chrome и IE8. Внутренний iframe ссылается на страницу, которая находится в том же домене, что и родительская страница.

В этом конкретном случае я скрываю элемент с определенным классом во внутреннем фрейме.

По сути, вы просто добавляете элемент «style» к «head» внутреннего iframe.

$('iframe').load( function() {
    $('iframe').contents().find("head")
      .append($("<style type='text/css'>  .my-class{display:none;}  </style>"));
});
SimpleSam5
источник
4
@ SimpleSam5 Можете ли вы предоставить альтернативу Javascript (без использования Jquery)?
Камалаканнан Дж.
1
@sincerekamal Вот код без использования jQuery: jsfiddle.net/9g9wkpon Вам просто нужно знать, что свойства CSS через дефис написаны в camelCase в JavaScript, как в моем примере. :)
Dennis98
2
jquery.js? ver = 1.12.4: 2 Uncaught DOMException: не удалось прочитать свойство 'contentDocument' из 'HTMLIFrameElement': заблокирован фрейм с источником " xxxxxxxxx.com " от доступа к фрейму перекрестного происхождения.
Алекс Станезе
2
@AlexStanese, как утверждает Джереми, это работает только в том случае, если страница iframe поступает с того же сервера, что и родительская страница ... что обычно означает, что вам в любом случае не нужно беспокоиться о javascript ... просто добавьте CSS на другую страницу в первую очередь.
DA.
@ KamalakannanJ вам даже не нужно использовать Javascript. Просто отредактируйте страницу в iFrame и поместите туда CSS.
DA.
25

Вы не можете изменить стиль страницы, отображаемой в iframe, если у вас нет прямого доступа и, следовательно, владения исходными файлами html и / или css.

Это должно остановить XSS (межсайтовый скриптинг)

Майлз Грей
источник
Что вы подразумеваете под «прямым доступом»? Страница в iframe с моего сайта, все это один домен.
jd6699
2
Что ж, тогда вам нужно будет изменить исходный файл на вашем сайте (вы не можете изменять любое содержимое в iframe) - поэтому, если iframe указывает на mysite.com/test.html, вам нужно будет напрямую изменить test.html .. .
Майлс Gray
1
Не может? При условиях ОП говорит, что вы можете. Например, его внутренний URL-адрес iframe такой же, как и у его родительского сайта, поэтому он должен иметь доступ к DOM нормально, с любым
OG Sean
@ Майлз Грей Неверно. Вы можете изменить содержимое в iframe с его родительской страницы, если оно находится в одном домене, как с помощью JavaScript, так и CSS.
Кевин М
8

У An iframeесть другая область действия, поэтому вы не можете получить к ней доступ к стилю или изменить его содержимое с помощью JavaScript.

Это в основном "другая страница".

Единственное, что вы можете сделать, это отредактировать свой собственный CSS, потому что с вашим глобальным CSS вы ничего не можете сделать.

Алессандро Вендрусколо
источник
Да, вы можете с помощью JavaScript. Обратите внимание, что он лучше всего работает с URL-адресом iframe и родительским URL-адресом, использующими один и тот же домен. Но я думаю, что вы правы, указывая, что это можно сделать с помощью CSS на странице внутри iframe.
О.Г. Шон
8

Переопределить другой домен iframe CSS

Используя часть ответа SimpleSam5 , я добился этого с помощью нескольких фреймов чата Tawk (их интерфейс настройки хорош, но мне потребовались дополнительные настройки).

В этом конкретном 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>")
   );
};

У меня нет домена Таука, и это сработало для меня, поэтому вы можете сделать это, даже если он не из того же родительского домена (несмотря на комментарий Джереми Беккера на ответ Сэма).

CPHPython
источник
18
Я подозреваю, что это работает только потому, что люди в Тауке явно разрешили это.
адвокат
@CPHPython Может быть, вы можете мне помочь. Посмотрите на это: stackoverflow.com/questions/60923168/…
Успех Человек
7

Этот код использует ванильный JavaScript. Это создает новый <style>элемент. Он устанавливает текстовое содержимое этого элемента как строку, содержащую новый CSS. И он добавляет этот элемент непосредственно в заголовок документа iframe.

var iframe = document.getElementById('the-iframe');
var style = document.createElement('style');
style.textContent =
  'body {' +
  '  background-color: some-color;' +
  '  background-image: some-image;' +
  '}' 
;
iframe.contentDocument.head.appendChild(style);
2540625
источник
7
Blocked a frame with origin xxxxxxxxx from accessing a cross-origin frame.Боюсь, это не сработает
Майк
1

Если у вас есть контроль над страницей, на которой размещен iframe, и страницей 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 ); 

Внутри рамки:

//add mobile class if needed
var url = new URL(window.location.href);
var isMobile = url.searchParams.get("isMobile");
if(isMobile == "1") {
    $("body").addClass("mobile");
}
Бен
источник
Возможно ты можешь помочь мне. Посмотрите на это: stackoverflow.com/questions/60923168/…
Успех Человек
0

У меня есть блог, и мне было очень трудно выяснить, как изменить размер встроенной сущности. Почтовый менеджер позволяет только писать текст, размещать изображения и вставлять HTML-код. Макет блога отзывчив на себя. Он построен с Wix. Однако встроенного HTML нет. Я много читал о том, как невозможно изменить размер компонентов внутри тела сгенерированных фреймов. Итак, вот мое предложение:

Если в вашем iFrame есть только один компонент, т. Е. Ваша сущность, вы можете изменить ее размер. Забудьте об iFrame.

У меня были проблемы с окном просмотра, конкретными макетами для различных пользовательских агентов, и вот что решило мою проблему:

<script language="javascript" type="text/javascript" src="https://gist.github.com/roliveiravictor/447f994a82238247f83919e75e391c6f.js"></script>

<script language="javascript" type="text/javascript">

function windowSize() {
  let gist = document.querySelector('#gist92442763');

  let isMobile = {
    Android: function() {
        return /Android/i.test(navigator.userAgent)
    },
    BlackBerry: function() {
        return /BlackBerry/i.test(navigator.userAgent)
    },
    iOS: function() {
        return /iPhone|iPod/i.test(navigator.userAgent)
    },
    Opera: function() {
        return /Opera Mini/i.test(navigator.userAgent)
    },
    Windows: function() {
        return /IEMobile/i.test(navigator.userAgent) || /WPDesktop/i.test(navigator.userAgent)
    },
    any: function() {
        return (isMobile.Android() || isMobile.BlackBerry() || isMobile.iOS() || isMobile.Opera() || isMobile.Windows());
    }
};

  if(isMobile.any()) {
    gist.style.width = "36%";
    gist.style.WebkitOverflowScrolling = "touch"
    gist.style.position = "absolute"
  } else {
    gist.style.width = "auto !important";
  }
}

windowSize();

window.addEventListener('onresize', function() {
    windowSize();
});

</script>

<style type="text/css">

.gist-data {
  max-height: 300px;
}

.gist-meta {
  display: none;
}

</style>

Логика заключается в том, чтобы установить gist (или ваш компонент) css на основе пользовательского агента. Убедитесь, что сначала идентифицировали свой компонент, прежде чем применять его к селектору запросов. Не стесняйтесь посмотреть, как работает отзывчивость .

Виктор Р. Оливейра
источник
-3

Возможно, теперь это изменилось, но я использовал отдельную таблицу стилей с этим элементом:

.feedEkList iframe
{
max-width: 435px!important;
width: 435px!important;
height: 320px!important;
}

для успешной стилизации встроенных фреймов YouTube ... см. записи блога на этой странице .

Тим Джексон
источник
4
Хотя эта ссылка может ответить на вопрос, лучше включить сюда основные части ответа и предоставить ссылку для справки. Ответы, содержащие только ссылки, могут стать недействительными, если связанная страница изменится.
Shaiful Islam
4
Это относится только к самому элементу iFrame - вопрос конкретно касается содержимого iFrame, которое в настоящее время невозможно изменить только с помощью CSS.
pwdst
@ShaifulIslam, это именно то, что произошло. Раздирающий Тимс отвечает бесполезно.
Алекс Фоксли,
-24

присвойте телу своей страницы iframe идентификатор (или класс, если хотите)

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

затем, также на странице iframe, назначьте фон в CSS

#myId {
    background-color: white;
}
mikeq
источник
Это странно Ваше решение работает для меня, когда я добавляю его на страницу с firebug, но не работает, если оно находится в обычном css-файле страницы. Может ли это быть частью вашего комментария «предполагая, что страница внутри iFrame принадлежит вам для редактирования»? Я не понял, что вы имели в виду под этим. Спасибо
jd6699
Я имею в виду, находится ли страница, которую вы загружаете в iFrame со своего сайта, под вашим контролем? или это с внешнего сайта, что вы не можете редактировать источник, чтобы включить этот идентификатор / класс.
Mikeq
Это с моего сайта, но, как это сделал редактор, будет нелегко изменить разметку, которая проходит через.
jd6699
PS Я не имел в виду добавить id = "myId" на вашу главную страницу, но на страницу внутри iFrame. Таким образом, вы можете настроить таргетинг основной части страницы iFrame на другую. Вы также ссылаетесь на CSS-файл на своих страницах iFrame. Вы должны рассматривать страницу, загруженную в iFrame, как полностью независимую страницу. Если вы загружаете только эту страницу в веб-браузер, имеет ли она правильный стиль?
mikeq
На самом деле я не уверен, где находится страница, так как это не вся страница, которую использует редактор. Спасибо за вашу помощь, я думаю, я понимаю, как все это работает, нет.
jd6699