加载 DOM 后在附加上执行 <script> 标记

4nd*_*ndy 3 javascript append vue.js

我正在尝试在模式中观看 onClick 视频,而无需访问视频页面本身。

我正在使用 Vue.js,通过一系列 Ajax 调用,我能够完成大部分工作。

Codpen: https: //codepen.io/nolaandy/pen/BrbBzO

如果您点击顶部的“对阵太阳队”,您会看到所有视频帖子的列表。然后单击任何图像,模式组件会弹出并动态获取帖子的标题。

我也想在那里运行视频,所以我尝试运行这个脚本标签:

 < script class="_nbaVideoPlayerScout" data-team="warriors" data-videoId="/video/{{unique videoId from post ajax call}}" data-width="768" data-height="732" src="https://www.nba.com/scout/team/cvp/videoPlayerScout.js"></script>
Run Code Online (Sandbox Code Playgroud)

当模式弹出时,我看到我单击的帖子/图像的正确标题,并且我看到脚本标签与检查器中应有的完全相同,但脚本标签从未运行。

我应该有什么不同的方式来注入这个脚本吗?(这是在 axios 响应调用内部)

let theVideoId = response.data.content[0].videoID


let s = document.createElement('script')
s.setAttribute('class', '_nbaVideoPlayerScout')
s.setAttribute('data-team', 'warriors') 
s.setAttribute('data-videoId', '/video/' + theVideoId) 
s.setAttribute('data-width', '768') 
s.setAttribute('data-height', '732') 
s.setAttribute('src', 'https://www.nba.com/scout/team/cvp/videoPlayerScout.js')
document.getElementById('popupVideo').appendChild(s);
Run Code Online (Sandbox Code Playgroud)

模态组件——点击帖子缩略图之一时触发

const videoModal = Vue.component('VideoModal', {
props: {
    id: {
    type: String,
    required: true
    }
},
data: function () {
  return {
    post: [],
  }
},
mounted() {
  const singleApi = 'https://cors-anywhere.herokuapp.com/www.nba.com/warriors/api/1.1/json?textformat=html&nid='
  axios.get(singleApi + this.id).then((response) => {
    this.post = response.data.content[0]
    console.log('THE RESPONSE', response)

    let theVideoId = response.data.content[0].videoID


let s = document.createElement('script')
s.setAttribute('class', '_nbaVideoPlayerScout')
s.setAttribute('data-team', 'warriors') 
s.setAttribute('data-videoId', '/video/' + theVideoId) 
s.setAttribute('data-width', '768') 
s.setAttribute('data-height', '732') 
s.setAttribute('src', 'https://www.nba.com/scout/team/cvp/videoPlayerScout.js')
document.getElementById('popupVideo').appendChild(s);
  }).catch((error) => {
    console.log(error)
  })

},
methods: {
  goBack: function () {
    router.go(-1)
  }
},
template:`<div>
<div id="video-popup">
  <button class="close-video-popup" @click="goBack">close me</button>
  <div class="video-popup-wrapper">
    <div class="video-popup--title">{{post.title}}</div>
    <div class="video-popup--video" id="popupVideo"></div>
  <div class="video-popup--share"></div>
</div>
</div>
</div>`
})
Run Code Online (Sandbox Code Playgroud)

小智 5

一时兴起,我做出了这样的改变:

// document.getElementById('scriptMe').appendChild(s);
document.body.appendChild(s);
Run Code Online (Sandbox Code Playgroud)

以及繁荣、脚本运行和视频加载。

这非常有趣,因为“为什么”,对吧?

编辑:此外,尝试此处讨论的其他脚本注入方法。

文档.write方法

document.write(s.outerHTML) // s is a script node
Run Code Online (Sandbox Code Playgroud)

也有效。事实上,您可以将该脚本节点嵌入到 a 中div,它也可以工作。

创建ContextualFragment方法

// var $container = document.getElementById('scriptMe'); // does not work
var $container = document.body
var range = document.createRange()
$container.appendChild(range.createContextualFragment(script_str))
Run Code Online (Sandbox Code Playgroud)

有效,其中script_str是 html 字符串文字。这将作为"<script>....</script>""<div id="myDiv"><script>...</script></div>"

但我测试的所有方法最终都需要在body.

代码笔