动态加载SVG并修改元素fillColor:onload事件未触发
解决SVG Object onload未触发及修改元素填充色问题
核心问题分析与解决步骤
必须将object元素添加到DOM中
创建的object元素如果未挂载到页面DOM树,浏览器不会发起资源加载请求,onload事件自然不会触发。添加一行代码将元素加入DOM即可(如果不需要页面显示,可设置隐藏):document.body.appendChild(img); img.style.display = 'none'; // 可选,不需要显示时隐藏修正填充色的修改逻辑
SVG元素的填充色不能用style.fillColor,正确的两种修改方式:- 通过DOM属性直接设置:
this.contentDocument.getElementById('K3').setAttribute('fill', 'yellow'); - 通过CSS样式设置:
this.contentDocument.getElementById('K3').style.fill = 'yellow';
- 通过DOM属性直接设置:
排查跨域与本地访问限制
- 确保SVG文件与当前页面同域,跨域资源会被浏览器限制访问
contentDocument; - 本地用
file://协议打开页面时,部分浏览器会限制SVG内容访问,建议用本地服务器(如http-server)运行页面。
- 确保SVG文件与当前页面同域,跨域资源会被浏览器限制访问
适配Three.js纹理更新
修改SVG后,需要通知Three.js更新纹理:// 假设texture是你创建的Three.Texture实例 texture.needsUpdate = true;
完整修正代码示例
var svgObj = document.createElement('object'); svgObj.data = 'texture.svg'; svgObj.type = 'image/svg+xml'; svgObj.style.display = 'none'; document.body.appendChild(svgObj); svgObj.onload = function () { try { const k3Element = this.contentDocument.getElementById('K3'); if (k3Element) { k3Element.setAttribute('fill', 'yellow'); console.log('K3元素填充色已修改'); // 更新Three.js纹理 // texture.needsUpdate = true; } else { console.error('未找到id为K3的SVG元素'); } } catch (e) { console.error('访问SVG内容失败:', e); } };
替代方案(无需object元素)
如果不想依赖DOM中的object元素,可以直接读取SVG文本内容修改后生成DataURL,再传给Three.js纹理:
// 用fetch读取SVG文件 fetch('texture.svg') .then(res => res.text()) .then(svgText => { // 替换K3元素的fill属性 const modifiedSvg = svgText.replace(/id="K3".*?fill="([^"]+)"/, 'id="K3" fill="yellow"'); // 生成DataURL const svgUrl = 'data:image/svg+xml,' + encodeURIComponent(modifiedSvg); // 创建Three.js纹理 const texture = new THREE.TextureLoader().load(svgUrl); // 应用到网格... });
内容的提问来源于stack exchange,提问作者arrowman
相关产品推荐
相关产品推荐

