是否可以使用 Javascript 将 css 样式表导入 html 页面?如果是这样,怎么办?
PS javascript 将托管在我的网站上,但我希望用户能够放入<head>
他们网站的标签,并且它应该能够将托管在我的服务器上的 css 文件导入当前网页。(css 文件和 javascript 文件都将托管在我的服务器上)。
是否可以使用 Javascript 将 css 样式表导入 html 页面?如果是这样,怎么办?
PS javascript 将托管在我的网站上,但我希望用户能够放入<head>
他们网站的标签,并且它应该能够将托管在我的服务器上的 css 文件导入当前网页。(css 文件和 javascript 文件都将托管在我的服务器上)。
这是“老派”的做法,希望它适用于所有浏览器。理论上,setAttribute
不幸的是,您会使用 IE6 并不能始终如一地支持它。
var cssId = 'myCss'; // you could encode the css path itself to generate id..
if (!document.getElementById(cssId))
{
var head = document.getElementsByTagName('head')[0];
var link = document.createElement('link');
link.id = cssId;
link.rel = 'stylesheet';
link.type = 'text/css';
link.href = 'http://website.com/css/stylesheet.css';
link.media = 'all';
head.appendChild(link);
}
此示例检查 CSS 是否已添加,因此仅添加一次。
将该代码放入 javascript 文件中,让最终用户简单地包含 javascript,并确保 CSS 路径是绝对路径,以便从您的服务器加载。
head
这是一个使用纯 JavaScript根据 URL 的文件名部分将 CSS 链接注入元素的示例:
<script type="text/javascript">
var file = location.pathname.split( "/" ).pop();
var link = document.createElement( "link" );
link.href = file.substr( 0, file.lastIndexOf( "." ) ) + ".css";
link.type = "text/css";
link.rel = "stylesheet";
link.media = "screen,print";
document.getElementsByTagName( "head" )[0].appendChild( link );
</script>
在结束标记之前插入代码head
,CSS 将在页面呈现之前加载。使用外部 JavaScript ( .js
) 文件将导致出现无样式内容 ( FOUC ) 的 Flash。
如果你使用 jquery:
$('head').append('<link rel="stylesheet" type="text/css" href="style.css">');
我想像这个脚本这样的东西会做:
<script type="text/javascript" src="/js/styles.js"></script>
该 JS 文件包含以下语句:
if (!document.getElementById) document.write('<link rel="stylesheet" type="text/css" href="/css/versions4.css">');
如果要引用您的站点,则 javascript 和 css 的地址必须是绝对地址。
这篇“用分支技术对 CSS hacks 说不”一文讨论了许多 CSS 导入技术。
但是“使用 JavaScript 动态添加 Portlet CSS 样式表”一文也提到了 CreateStyleSheet 可能性(IE 的专有方法):
<script type="text/javascript">
//<![CDATA[
if(document.createStyleSheet) {
document.createStyleSheet('http://server/stylesheet.css');
}
else {
var styles = "@import url(' http://server/stylesheet.css ');";
var newSS=document.createElement('link');
newSS.rel='stylesheet';
newSS.href='data:text/css,'+escape(styles);
document.getElementsByTagName("head")[0].appendChild(newSS);
}
//]]>
Element.insertAdjacentHTML有很好的浏览器支持,可以一行添加一个样式表。
document.getElementsByTagName("head")[0].insertAdjacentHTML(
"beforeend",
"<link rel=\"stylesheet\" href=\"path/to/style.css\" />");
如果您想知道(或等待)直到样式本身已加载,这可行:
// this will work in IE 10, 11 and Safari/Chrome/Firefox/Edge
// add ES6 poly-fill for the Promise, if needed (or rewrite to use a callback)
let fetchStyle = function(url) {
return new Promise((resolve, reject) => {
let link = document.createElement('link');
link.type = 'text/css';
link.rel = 'stylesheet';
link.onload = function() { resolve(); console.log('style has loaded'); };
link.href = url;
let headScript = document.querySelector('script');
headScript.parentNode.insertBefore(link, headScript);
});
};
在现代浏览器中,您可以promise
像这样使用。创建一个带有承诺的加载器函数:
function LoadCSS( cssURL ) {
// 'cssURL' is the stylesheet's URL, i.e. /css/styles.css
return new Promise( function( resolve, reject ) {
var link = document.createElement( 'link' );
link.rel = 'stylesheet';
link.href = cssURL;
document.head.appendChild( link );
link.onload = function() {
resolve();
console.log( 'CSS has loaded!' );
};
} );
}
那么显然你想要在 CSS 加载后完成一些事情。您可以像这样调用 CSS 加载后需要运行的函数:
LoadCSS( 'css/styles.css' ).then( function() {
console.log( 'Another function is triggered after CSS had been loaded.' );
return DoAfterCSSHasLoaded();
} );
如果您想深入了解它是如何工作的,有用的链接:
使用此代码:
var element = document.createElement("link");
element.setAttribute("rel", "stylesheet");
element.setAttribute("type", "text/css");
element.setAttribute("href", "external.css");
document.getElementsByTagName("head")[0].appendChild(element);
我知道这是一个很老的话题,但我的 5 美分来了。
根据您的需求,还有另一种方法可以做到这一点。
我有一个案例,我希望一个 css 文件只激活一段时间。就像css切换一样。激活 css,然后在另一个事件之后将其停用。
您可以在新 css 中的所有元素前面添加一个类/一个 id,而不是动态加载 css 然后将其删除,然后只需切换 css 基节点的类/id(如 body 标记)。
使用此解决方案,您最初会加载更多的 css 文件,但您有一种更动态的方式来切换 css 布局。
你听说过承诺吗?它们适用于所有现代浏览器,并且使用起来相对简单。看看这个将 css 注入 html 头部的简单方法:
function loadStyle(src) {
return new Promise(function (resolve, reject) {
let link = document.createElement('link');
link.href = src;
link.rel = 'stylesheet';
link.onload = () => resolve(link);
link.onerror = () => reject(new Error(`Style load error for ${src}`));
document.head.append(link);
});
}
您可以按如下方式实现它:
window.onload = function () {
loadStyle("https://fonts.googleapis.com/css2?family=Raleway&display=swap")
.then(() => loadStyle("css/style.css"))
.then(() => loadStyle("css/icomoon.css"))
.then(() => {
alert('All styles are loaded!');
}).catch(err => alert(err));
}
真的很酷,对吧?这是一种使用 Promises 决定样式优先级的方法。
要查看多样式加载实现,请参阅:https ://stackoverflow.com/a/63936671/13720928
有一个通用的 jquery 插件,可以按需加载 css 和 JS 文件同步和异步。它还跟踪已经加载的内容:) 请参阅:http ://code.google.com/p/rloader/
这是 jQuery 的元素创建方法(我的偏好)和回调的一种方式onLoad
:
var css = $("<link>", {
"rel" : "stylesheet",
"type" : "text/css",
"href" : "style.css"
})[0];
css.onload = function(){
console.log("CSS IN IFRAME LOADED");
};
document
.getElementsByTagName("head")[0]
.appendChild(css);
下面是用于加载 JS 和/或 CSS 的完整代码
function loadScript(directory, files){
var head = document.getElementsByTagName("head")[0]
var done = false
var extension = '.js'
for (var file of files){
var path = directory + file + extension
var script = document.createElement("script")
script.src = path
script.type = "text/javascript"
script.onload = script.onreadystatechange = function() {
if ( !done && (!this.readyState ||
this.readyState == "loaded" || this.readyState == "complete") ) {
done = true
script.onload = script.onreadystatechange = null // cleans up a little memory:
head.removeChild(script) // to avoid douple loading
}
};
head.appendChild(script)
done = false
}
}
function loadStyle(directory, files){
var head = document.getElementsByTagName("head")[0]
var extension = '.css'
for (var file of files){
var path = directory + file + extension
var link = document.createElement("link")
link.href = path
link.type = "text/css"
link.rel = "stylesheet"
head.appendChild(link)
}
}
(() => loadScript('libraries/', ['listen','functions', 'speak', 'commands', 'wsBrowser', 'main'])) ();
(() => loadScript('scripts/', ['index'])) ();
(() => loadStyle('styles/', ['index'])) ();
这是一个单行示例,它使用纯 JavaScript 根据 URL 的文件名部分将 CSS 链接注入到 head 元素中:
document.head.innerHTML += '<link rel="stylesheet" href="css/style.css">';
大多数浏览器都支持它。查看浏览器兼容性。
我想分享另一种方法,不仅可以加载 css,还可以加载所有资产(js、css、图像)并处理一堆文件的onload事件。是async-assets-loader
。请参见下面的示例:
<script src="https://unpkg.com/async-assets-loader"></script>
<script>
var jsfile = "https://code.jquery.com/jquery-3.4.1.min.js";
var cssfile = "https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0/css/materialize.min.css";
var imgfile = "https://logos.keycdn.com/keycdn-logo-black.png";
var assetsLoader = new asyncAssetsLoader();
assetsLoader.load([
{uri: jsfile, type: "script"},
{uri: cssfile, type: "style"},
{uri: imgfile, type: "img"}
], function () {
console.log("Assets are loaded");
console.log("Img width: " + assetsLoader.getLoadedTags()[imgfile].width);
});
</script>
var elem = document.createElement('link');
elem.rel = ' stylesheet'
elem.href= 'style.css';//Link of the css file
document.head.appendChild(elem);
var fileref = document.createElement("link")
fileref.setAttribute("rel", "stylesheet")
fileref.setAttribute("type", "text/css")
fileref.setAttribute("th:href", "@{/filepath}")
fileref.setAttribute("href", "/filepath")
我正在使用百里香,这很好用。谢谢
采用:
document.getElementById("of head/body tag")
.innerHTML += '<link rel="stylesheet" type="text/css" href="style.css">';