我的网站上有一个歌曲提交表单。当艺术家上传一首歌时,我开发了JS来计算每分钟的节拍(BPM)和歌曲的持续时间。计算完成后,它会填充表单上的两个相应输入框(持续时间和BPM)。如果提交了一首歌曲,我的代码就完美无缺,但是,该表单允许每个表单提交多个歌曲上传。由于这些新的输入框是动态添加的,我不太确定如何让新歌动态更新bpm / duration的值,因为新的输入框是由JS加载的。下面有相当数量的代码,如果您需要更多说明,请与我们联系:
用户可以通过点击"添加另一首歌曲来动态添加另一首歌曲#34;通过JS加载按钮:
<div id="dynamicInput"></div>
<input type="button" id="add-song-btn" value="Add another song" onClick="addInput('dynamicInput');">
相应的JS:
var counter = 1;
var limit = 20;
function addInput(divName)
{
if(counter == limit)
{
alert("You have reached the limit of adding " + counter + " inputs");
}
else
{
var newdiv = document.createElement('div');
{
newdiv.innerHTML = "<hr>Song #" + (counter + 1) + " " + "<input type='hidden' role='uploadcare-uploader' data-max-size='120000000' name='song-submission'data-crop='disabled' /><input type='text' id='duration' name='submit-duration' placeholder='Duration: '3:11'><input type='number' id='bpm' name='submit-bpm' placeholder='BPM: 128'>";
document.getElementById(divName).appendChild(newdiv);
}
counter++;
setTimeout(function () {
uploadcare.initialize();
}, 0);
}
};
当用户使用&#34;选择文件&#34;上传歌曲时按钮,这是相应的输入框:
<input name="song-submission" type="hidden" role="uploadcare-uploader" data-max-size="120000000" data-file-types="mp3" data-crop="disabled">
上传时,提交会创建一个src网址,我将其添加到音频HTML src标记中,该标记会触发两个不同的JS函数。上传完成后,JS代码widget.onUploadComplete
运行。这里是音频标记以及将src网址加载到该html代码中的相应代码:
<audio id="myAudio" controls onloadedmetadata="setDuration()">
<source src="">
</audio>
JS
var widget = uploadcare.Widget('[role=uploadcare-uploader]');
widget.onUploadComplete(function(info) {
var previewUrl = info.cdnUrl;
document.getElementById('myAudio').src = info.cdnUrl;
//code to calculate BPM is found here///
document.getElementById('bpm').value = Math.round(top[0].tempo);
};
};
request.send();
});
当src url添加到HTML音频id="myAudio"
标记时,JS会等到onloadedmetadata
运行函数(setDuration()
)以确定持续时间:
function setDuration() {
var time = document.getElementById('myAudio').duration;
// code to calculate duration //
ret += "" + mins + ":" + (secs < 10 ? "0" : "");
ret += "" + Math.round(secs);
document.getElementById('duration').value = ret;
return ret;
}
所以这就是我所处的位置,而且我的代码不适用于动态加载的输入框。首先,一旦添加了新的歌曲提交输入,就会有两个带有role=uploadcare-uploader
的输入框,这会导致widget
JS变量出现问题,我认为这样做了。我们需要先开始的地方。有什么想法吗?
答案 0 :(得分:1)
当您初始化新的uplaodcare实例(延迟)时,它不会为那些新创建的小部件注册onUploadComplete
个事件,因为仅在您执行uploadcare.Widget('[role=uploadcare-uploader]');
第一个孩子的那一刻(您的另一个问题)代码)获取注册的事件监听器。
元素参数可以是DOM元素,jQuery对象或CSS选择器。 &gt;如果element的参数是CSS选择器,则只返回第一个&gt;匹配元素的实例。为确保您获得正确的实例&gt;当页面上有多个小部件时,请按ID选择或传入DOM元素。
在每个uploadcare实例创建后执行代码并使用唯一选择器来获取适当的小部件:
setTimeout(function () {
uploadcare.initialize();
var widget = uploadcare.Widget('#song-uploader-<1..N>'); // Generate this when DIV adding
widget.onUploadComplete(function(info) {
var previewUrl = info.cdnUrl;
document.getElementById('myAudio').src = info.cdnUrl;
//code to calculate BPM is found here///
document.getElementById('bpm').value = Math.round(top[0].tempo);
};
};
request.send();
});
}, 0);
您可以将处理程序省略到自己的函数中以保持代码清洁并编写widget.onUploadComplete(calculateBPM)
答案 1 :(得分:0)
它说:
初始化窗口小部件实例一次(单个上载,或 在每个元素上使用role =“uploadcare-uploader”进行多上传 容器中的属性,由selector或DOM元素指定。如果 容器没有使用文件。返回new的数组 初始化小部件,如果没有新实例则为空数组 初始化。
var widgets = uploadcare.initialize('#my-form');
widgets; // [widget1, widget2, multipleWidget1, ...]
var widgets = uploadcare.initialize();
从那时起你就可以继续了。 (例如,给输入框一个id,并在每个带有该id的输入框上调用你的js函数)。