Javascript-форум (https://javascript.ru/forum/)
-   Events/DOM/Window (https://javascript.ru/forum/events/)
-   -   Ошибка загрузки CSS по событию... (https://javascript.ru/forum/events/29693-oshibka-zagruzki-css-po-sobytiyu.html)

Vision 07.07.2012 17:10

Ошибка загрузки CSS по событию...
 
Вложений: 1
Добрый день. Уважаемые форумчане, столкнулся с необъяснимой для меня проблемой на ровном месте.
Имеется следующий код:
Код:

<!DOCTYPE html>
<html>
<head>
    <meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
    <title>Demo</title>
    <link id="cssStyle" href="" rel="stylesheet" type="text/css">
    <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
    <script type="text/javascript">
        function loadfirst() {$("#cssStyle").attr("href","1.css");alert($(".some").width())}
        function loadsecond() {$("#cssStyle").attr("href","2.css");alert($(".some").width())}
        window.onorientationchange = function() {
          var ww = $(window).width();
          var wh = $(window).height();
          if(ww>wh) {alert("landscape");loadsecond()}
            else {alert("portraite");loadfirst()}
        }
    </script>
</head>

<body>
    <a href="#" onclick="loadfirst();">First css load</a>
    <a href="#" onclick="loadsecond();">Second css load</a>
    <div class="some"></div>
</body>

</html>

Имеется две ссылки, при нажатии на которые подгружается соответствующий стиль (стили подгружаются также при смены ориентации дисплея(для мобилок)).
Файл 1.css:
Код:

.some {
  width:111px;
  height:20px;
  background-color: #1144CC;
}

И файл 2.css:
Код:

.some {
  width:222px;
  height:20px;
  background-color: #1144CC;
}

В итоге после загрузки первого стиля должен вылезть alert со значением 111, а после второго - 222 соответственно. Но при первоначальной загрузке документа и нажатии на любую ссылку - вылазит alert со значением ширины окна! А должен содержать значение ширины элемента .some! Если страницу обновить и опять нажать на любую ссылку - получим верное значение. Но вот на мобильных девайсах (пример айфон) сколько не обновляй - первый клик по ссылке дает ошибочное значение.
Помогите, кто знает решение проблемы!!! ломаю мозг над решением уже неделю, безрезультатно... архивчик с исходником прилагаю

p.s. Еще глюк - загружаем страницу, жмем на 2й ссылке, получаем алерт с кривым значением, жмем ок, жмем на 1й ссылке - вместо "111" получаем "222", т.е. то значение, которое загрузилось перед этим (но тем не менее не показалось), следующие клики уже дают нужный результат. Взрыв мозга

Deff 07.07.2012 17:15

Vision,
1. Смена href="" в линке не означает действительно полную смену стиля - стили складываются последующий накладывается на предыдущий
для реальной смены необходимо ремовить тег и а потом его добавлять заново на страницу уже с новой ссылкой

А дважды из-за того то первый раз вы меняете href в линке, а при обновлении он единственный и неповторимый - а не подмененный

Vision 07.07.2012 17:42

Спасибо за быстрый ответ! Идея решения понятная, а вот реализация не совсем. Вот что наваял, глюки те же, а может даже и больше:
<!DOCTYPE html>
<html>
<head>
    <meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
    <title>Demo</title>
    <link id="cssStyle" />
    <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
    <script type="text/javascript">
        function loadfirst() {
          $("#cssStyle").remove();
          var css_link = $("<link>", {id: "cssStyle", rel: "stylesheet", type: "text/css", href: "1.css"});
          css_link.appendTo("head");
          alert($(".some").width());
          }
        function loadsecond() {
          $("#cssStyle").remove();
          var css_link = $("<link>", {id: "cssStyle", rel: "stylesheet", type: "text/css", href: "2.css"});
          css_link.appendTo("head");
          alert($(".some").width());
          }
        window.onorientationchange = function() {
          var ww = $(window).width();
          var wh = $(window).height();
          if(ww>wh) {alert("landscape");loadsecond()}
            else {alert("portraite");loadfirst()};
            return false;
        }
    </script>
</head>

<body>
    <a href="#" onclick="loadfirst();">First css load</a>
    <a href="#" onclick="loadsecond();">Second css load</a>
    <div class="some"></div>
</body>

</html>

Deff 07.07.2012 17:44

Vision,
http://javascript.ru/forum/job/28097...tml#post176656

Vision 07.07.2012 18:42

Deff,
Спасибо, сделал по образу и подобию - НЕ работает!
Ошибки те же, неверное значение при первой загрузке
<!DOCTYPE html>
<html>
<head>
    <meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
    <title>Demo</title>
    <link rel="stylesheet" type="text/css" href=">
    <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
    <style>#changeStyle img{border:solid 2px transparent;}
    .STYLselect {border-color:red!important;}
    </style>
</head>
<body>
<script type="text/javascript">
var linkStyles = '<link rel="stylesheet" type="text/css" href="';

function setcookie(a, b, c) {
    if (c) {
        var d = new Date();
        d.setDate(d.getDate() + c);
    }
    if (a && b) document.cookie = a + '=' + b + (c ? '; expires=' + d.toUTCString() : '');
    else return false;
}

function getcookie(a) {
    var b = new RegExp(a + '=([^;]){1,}');
    var c = b.exec(document.cookie);
    if (c) c = c[0].split('=');
    else return false;
    return c[1] ? c[1] : false;
}

function clearSet(L) {
    if (L) {
        setcookie("changeStyle", L, 30);
        $("link[rel='stylesheet']:first").replaceWith(linkStyles + L + '"/>');
    }
};
var Lmem = getcookie("changeStyle");
clearSet(Lmem);
</script>
<div id="changeStyle" style="top:0; left: 3px; position:fixed!important;">
<img src="http://www.10pix.ru/img1/3444/5439522.jpg" alt="1.css"/>
<br>
<img src="http://www.10pix.ru/img1/3492/5439523.jpg" alt="2.css"/>
<br>
</div>
<script>
    $("#changeStyle img[alt='" + Lmem + "']").addClass("STYLselect");
    $('#changeStyle img[alt]').click(function () {
        L = $(this).attr("alt");
        $('#changeStyle img[alt]').removeClass("STYLselect");
        $(this).addClass("STYLselect");
        clearSet(L);
        alert($(".some").width());
    });
</script>
<br /><br /><br /><br /><br />
<div class="some"></div>
</body>
</html>

Deff 07.07.2012 18:51

Vision,
попробуйте обрамить
$(window).load(function () {
  alert($(".some").width());
});


(стиль меняется не одномоментно

Vision 07.07.2012 19:47

Deff,
вызов функции $(window).load внутри $('#changeStyle img[alt]').click(function (...)) никогда не сработает. А вызов этой же функции извне возвращает значение загруженной css в самом начале, если же в моем случае первоначальное href="" то и значение принимает значение ширины окна. Задача в том и состоит, чтобы после загрузки страницы, по некоторому событию загрузить соответствующий стиль и получить из него значения некоторых величин, в одном и том же скрипте.

vadim5june 07.07.2012 20:08

Цитата:

Сообщение от Vision (Сообщение 187098)
Задача в том и состоит, чтобы после загрузки страницы, по некоторому событию загрузить соответствующий стиль и получить из него значения некоторых величин, в одном и том же скрипте.

По мне так Вы выбрали сложный путь для решение задачи-динамической подгрузки css надо избегать по возможности
когда Вы пишите такую строчку
{$("#cssStyle").attr("href","1.css");alert($(".som e").width()
то после установки нового значения href нужно время чтобы файл загрузился а Вы сразу хотите получить результат его работы
Кроме того при загрузке css по моему не работает onload и мы не узнаем когда же загрузился очередной файл
Я бы предложил сделать два класса some1 и some2-которые загрузятся сразу а потом просто менять атрибут class
либо просто менять стилями-если это возможно

Deff 07.07.2012 20:20

Vision,
Цитата:

Сообщение от Vision
вызов функции $(window).load внутри $('#changeStyle img[alt]').click(function (...))

Гы - наверно вы правы,

тады так:
<script type="text/javascript">
var W=false;
function TstWidth() {
  var s=100; //
  var W2=false;
  if($(".some").length){var W2 = $(".some").width();return true;
    if(W2!=false&&(W2-W)==0){alert(W)}
  }
  timerId01=setTimeout(function(){TstWidth()},s);return;}
}
</script>
<script type="text/javascript">
    $("#changeStyle img[alt='" + Lmem + "']").addClass("STYLselect");
    $('#changeStyle img[alt]').click(function () {
        L = $(this).attr("alt");
        $('#changeStyle img[alt]').removeClass("STYLselect");
        $(this).addClass("STYLselect");
        clearSet(L);
        TstWidth()
    });
</script>

Vision 07.07.2012 20:22

Пробовал еще такой вариант - setTimeout(function() { someCSSload(); }, 2000); - иногда работает правильно, иногда не очень. vadim5june, а вот Ваша идея с переключением классов должна сработать. Но чувствую что мне еще придется к Вам обратится. Спасибо большое за помощь!
Deff Ваша конструкция интересна, сейчас опробую


Часовой пояс GMT +3, время: 10:45.