CC-5108 : Waveform Editor UI
putting on the timescale for time reference. fade editor now has cursor playback info.
This commit is contained in:
parent
16bd407136
commit
75e6f21ce0
10 changed files with 141 additions and 14 deletions
|
@ -36,6 +36,7 @@
|
||||||
|
|
||||||
<script id="tmpl-pl-cues" type="text/template">
|
<script id="tmpl-pl-cues" type="text/template">
|
||||||
<div class="waveform-cues">
|
<div class="waveform-cues">
|
||||||
|
<div class="playlist-time-scale"></div>
|
||||||
<div class="playlist-tracks"></div>
|
<div class="playlist-tracks"></div>
|
||||||
<div class="playlist-controls">
|
<div class="playlist-controls">
|
||||||
<a class="btn btn-small btn_play"><i class="icon-play icon-white"></i><?php echo _("Play"); ?></a>
|
<a class="btn btn-small btn_play"><i class="icon-play icon-white"></i><?php echo _("Play"); ?></a>
|
||||||
|
@ -61,10 +62,12 @@
|
||||||
|
|
||||||
<script id="tmpl-pl-fades" type="text/template">
|
<script id="tmpl-pl-fades" type="text/template">
|
||||||
<div class="waveform-fades">
|
<div class="waveform-fades">
|
||||||
|
<div class="playlist-time-scale"></div>
|
||||||
<div class="playlist-tracks"></div>
|
<div class="playlist-tracks"></div>
|
||||||
<div class="playlist-controls left-floated">
|
<div class="playlist-controls left-floated">
|
||||||
<a class="btn btn-small btn_play"><i class="icon-play icon-white"></i><?php echo _("Play"); ?></a>
|
<a class="btn btn-small btn_play"><i class="icon-play icon-white"></i><?php echo _("Play"); ?></a>
|
||||||
<a class="btn btn-small btn_stop"><i class="icon-stop icon-white"></i><?php echo _("Stop"); ?></a>
|
<a class="btn btn-small btn_stop"><i class="icon-stop icon-white"></i><?php echo _("Stop"); ?></a>
|
||||||
|
<label class="audio audio_pos">00:00:00.0</label>
|
||||||
</div>
|
</div>
|
||||||
<div class="set-fade left-floated">
|
<div class="set-fade left-floated">
|
||||||
<a type="button" class="btn btn-small btn_cursor" data-state="cursor"><?php echo _("Cursor"); ?></a>
|
<a type="button" class="btn btn-small btn_cursor" data-state="cursor"><?php echo _("Cursor"); ?></a>
|
||||||
|
|
|
@ -687,6 +687,10 @@ SQL;
|
||||||
{
|
{
|
||||||
$this->con->beginTransaction();
|
$this->con->beginTransaction();
|
||||||
|
|
||||||
|
if (!isset($offset)) {
|
||||||
|
$offset = Application_Model_Preference::GetDefaultCrossfadeDuration();
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (isset($id1)) {
|
if (isset($id1)) {
|
||||||
$this->changeFadeInfo($id1, null, $fadeOut);
|
$this->changeFadeInfo($id1, null, $fadeOut);
|
||||||
|
|
|
@ -673,6 +673,10 @@ SQL;
|
||||||
{
|
{
|
||||||
$this->con->beginTransaction();
|
$this->con->beginTransaction();
|
||||||
|
|
||||||
|
if (!isset($offset)) {
|
||||||
|
$offset = Application_Model_Preference::GetDefaultCrossfadeDuration();
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (isset($id1)) {
|
if (isset($id1)) {
|
||||||
$this->changeFadeInfo($id1, null, $fadeOut);
|
$this->changeFadeInfo($id1, null, $fadeOut);
|
||||||
|
|
|
@ -528,8 +528,6 @@ SQL;
|
||||||
*/
|
*/
|
||||||
public function getRelativeFileUrl($baseUrl)
|
public function getRelativeFileUrl($baseUrl)
|
||||||
{
|
{
|
||||||
Logging::debug("Zend base url: $baseUrl");
|
|
||||||
|
|
||||||
return $baseUrl."api/get-media/file/".$this->getId().".".$this->getFileExtension();
|
return $baseUrl."api/get-media/file/".$this->getId().".".$this->getFileExtension();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -14,11 +14,36 @@
|
||||||
.btn-small {
|
.btn-small {
|
||||||
/*line-height: 20px;*/
|
/*line-height: 20px;*/
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.playlist-time-scale {
|
||||||
|
position: absolute;
|
||||||
|
top: 5px;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
height: 30px;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
.playlist-time-scale canvas {
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
height: 30px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.playlist-time-scale div {
|
||||||
|
position: absolute;
|
||||||
|
}
|
||||||
|
|
||||||
.playlist-tracks {
|
.playlist-tracks {
|
||||||
margin: 8px 0;
|
position: relative;
|
||||||
|
top: 35px;
|
||||||
|
margin: 2px 0;
|
||||||
}
|
}
|
||||||
.playlist-controls {
|
.playlist-controls {
|
||||||
margin: 0 0 16px 0;
|
margin: 40px 0 16px 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.channel-wrapper {
|
.channel-wrapper {
|
||||||
|
@ -30,6 +55,8 @@
|
||||||
margin: 0;
|
margin: 0;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
background: #6e6e6e;
|
background: #6e6e6e;
|
||||||
|
/*border-top: 1px solid #6e6e6e;*/
|
||||||
|
/*border-bottom: 1px solid #6e6e6e;*/
|
||||||
}
|
}
|
||||||
|
|
||||||
.state-select {
|
.state-select {
|
||||||
|
@ -41,6 +68,12 @@
|
||||||
overflow-y: hidden;
|
overflow-y: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.playlist-tracks > .error {
|
||||||
|
height: 80px;
|
||||||
|
width: 300px;
|
||||||
|
background-color: rgba(255,0,0,0.5);
|
||||||
|
}
|
||||||
|
|
||||||
.playlist-fade {
|
.playlist-fade {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
background-color: rgba(0,0,0,0.1);
|
background-color: rgba(0,0,0,0.1);
|
||||||
|
@ -50,7 +83,7 @@
|
||||||
margin: 12px 0 16px 0;
|
margin: 12px 0 16px 0;
|
||||||
}
|
}
|
||||||
.set-fade {
|
.set-fade {
|
||||||
margin: 0 0 0 30px;
|
margin: 40px 0 0 30px;
|
||||||
}
|
}
|
||||||
.set-cue input[type="text"] {
|
.set-cue input[type="text"] {
|
||||||
vertical-align: middle;
|
vertical-align: middle;
|
||||||
|
|
|
@ -1246,7 +1246,7 @@ var AIRTIME = (function(AIRTIME){
|
||||||
show: 'clip',
|
show: 'clip',
|
||||||
hide: 'clip',
|
hide: 'clip',
|
||||||
width: dim.width - 100,
|
width: dim.width - 100,
|
||||||
height: dim.height - 100,
|
height: 350,
|
||||||
buttons: [
|
buttons: [
|
||||||
{text: $.i18n._("Cancel"), class: "btn btn-small", click: removeDialog},
|
{text: $.i18n._("Cancel"), class: "btn btn-small", click: removeDialog},
|
||||||
{text: $.i18n._("Save"), class: "btn btn-small btn-inverse", click: function() {
|
{text: $.i18n._("Save"), class: "btn btn-small btn-inverse", click: function() {
|
||||||
|
@ -1263,9 +1263,11 @@ var AIRTIME = (function(AIRTIME){
|
||||||
|
|
||||||
if (fade["type"] === "FadeOut") {
|
if (fade["type"] === "FadeOut") {
|
||||||
fadeOut = fade["end"] - fade["start"];
|
fadeOut = fade["end"] - fade["start"];
|
||||||
|
id2 = undefined; //incase of track decode error.
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
fadeIn = fade["end"] - fade["start"];
|
fadeIn = fade["end"] - fade["start"];
|
||||||
|
id1 = undefined; //incase of track decode error.
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
@ -1291,6 +1293,7 @@ var AIRTIME = (function(AIRTIME){
|
||||||
resolution: 15000,
|
resolution: 15000,
|
||||||
state: "cursor",
|
state: "cursor",
|
||||||
mono: true,
|
mono: true,
|
||||||
|
timescale: true,
|
||||||
waveHeight: 80,
|
waveHeight: 80,
|
||||||
container: $html[0],
|
container: $html[0],
|
||||||
UITheme: "jQueryUI",
|
UITheme: "jQueryUI",
|
||||||
|
@ -1301,7 +1304,10 @@ var AIRTIME = (function(AIRTIME){
|
||||||
playlistEditor.setConfig(config);
|
playlistEditor.setConfig(config);
|
||||||
playlistEditor.init(tracks);
|
playlistEditor.init(tracks);
|
||||||
},
|
},
|
||||||
close: removeDialog
|
close: removeDialog,
|
||||||
|
resizeStop: function(event, ui) {
|
||||||
|
playlistEditor.resize();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -1354,7 +1360,7 @@ var AIRTIME = (function(AIRTIME){
|
||||||
show: 'clip',
|
show: 'clip',
|
||||||
hide: 'clip',
|
hide: 'clip',
|
||||||
width: dim.width - 100,
|
width: dim.width - 100,
|
||||||
height: dim.height - 100,
|
height: 325,
|
||||||
buttons: [
|
buttons: [
|
||||||
{text: $.i18n._("Cancel"), class: "btn btn-small", click: removeDialog},
|
{text: $.i18n._("Cancel"), class: "btn btn-small", click: removeDialog},
|
||||||
{text: $.i18n._("Save"), class: "btn btn-small btn-inverse", click: function() {
|
{text: $.i18n._("Save"), class: "btn btn-small btn-inverse", click: function() {
|
||||||
|
@ -1371,6 +1377,7 @@ var AIRTIME = (function(AIRTIME){
|
||||||
var config = new Config({
|
var config = new Config({
|
||||||
resolution: 15000,
|
resolution: 15000,
|
||||||
mono: true,
|
mono: true,
|
||||||
|
timescale: true,
|
||||||
waveHeight: 80,
|
waveHeight: 80,
|
||||||
container: $html[0],
|
container: $html[0],
|
||||||
UITheme: "jQueryUI",
|
UITheme: "jQueryUI",
|
||||||
|
@ -1381,7 +1388,10 @@ var AIRTIME = (function(AIRTIME){
|
||||||
playlistEditor.setConfig(config);
|
playlistEditor.setConfig(config);
|
||||||
playlistEditor.init(tracks);
|
playlistEditor.init(tracks);
|
||||||
},
|
},
|
||||||
close: removeDialog
|
close: removeDialog,
|
||||||
|
resizeStop: function(event, ui) {
|
||||||
|
playlistEditor.resize();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -56,6 +56,16 @@ PlaylistEditor.prototype.init = function(tracks) {
|
||||||
trackEditor.on("deactivateSelection", "onAudioDeselection", audioControls);
|
trackEditor.on("deactivateSelection", "onAudioDeselection", audioControls);
|
||||||
trackEditor.on("changecursor", "onCursorSelection", audioControls);
|
trackEditor.on("changecursor", "onCursorSelection", audioControls);
|
||||||
trackEditor.on("changecursor", "onSelectUpdate", this);
|
trackEditor.on("changecursor", "onSelectUpdate", this);
|
||||||
|
|
||||||
|
trackEditor.on("unregister", (function() {
|
||||||
|
var editor = this;
|
||||||
|
|
||||||
|
audioControls.remove("trackedit", "onTrackEdit", editor);
|
||||||
|
audioControls.remove("changeresolution", "onResolutionChange", editor);
|
||||||
|
|
||||||
|
that.removeTrack(editor);
|
||||||
|
|
||||||
|
}).bind(trackEditor));
|
||||||
}
|
}
|
||||||
|
|
||||||
div.innerHTML = '';
|
div.innerHTML = '';
|
||||||
|
@ -82,6 +92,26 @@ PlaylistEditor.prototype.init = function(tracks) {
|
||||||
audioControls.on("changeselection", "onSelectionChange", this);
|
audioControls.on("changeselection", "onSelectionChange", this);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
PlaylistEditor.prototype.removeTrack = function(trackEditor) {
|
||||||
|
var i,
|
||||||
|
len,
|
||||||
|
editor,
|
||||||
|
editors = this.trackEditors;
|
||||||
|
|
||||||
|
for (i = 0, len = editors.length; i < len; i++) {
|
||||||
|
editor = editors[i];
|
||||||
|
|
||||||
|
if (editor === trackEditor) {
|
||||||
|
editors.splice(i, 1);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
PlaylistEditor.prototype.resize = function() {
|
||||||
|
this.timeScale.onResize();
|
||||||
|
};
|
||||||
|
|
||||||
PlaylistEditor.prototype.onTrimAudio = function() {
|
PlaylistEditor.prototype.onTrimAudio = function() {
|
||||||
var track = this.activeTrack,
|
var track = this.activeTrack,
|
||||||
selected = track.getSelectedArea(),
|
selected = track.getSelectedArea(),
|
||||||
|
|
|
@ -84,6 +84,7 @@ AudioPlayout.prototype.loadData = function (audioData, cb) {
|
||||||
},
|
},
|
||||||
function(err) {
|
function(err) {
|
||||||
console.log("err(decodeAudioData): "+err);
|
console.log("err(decodeAudioData): "+err);
|
||||||
|
cb(null, err);
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
@ -8,7 +8,8 @@ TimeScale.prototype.init = function(config) {
|
||||||
|
|
||||||
var that = this,
|
var that = this,
|
||||||
canv,
|
canv,
|
||||||
div;
|
div,
|
||||||
|
resizeTimer;
|
||||||
|
|
||||||
makePublisher(this);
|
makePublisher(this);
|
||||||
|
|
||||||
|
@ -36,6 +37,24 @@ TimeScale.prototype.init = function(config) {
|
||||||
|
|
||||||
this.prevScrollPos = 0; //checking the horizontal scroll (must update timeline above in case of change)
|
this.prevScrollPos = 0; //checking the horizontal scroll (must update timeline above in case of change)
|
||||||
|
|
||||||
|
//TODO check scroll adjust.
|
||||||
|
function doneResizing() {
|
||||||
|
that.width = that.container.clientWidth;
|
||||||
|
that.height = that.container.clientHeight;
|
||||||
|
|
||||||
|
canv.setAttribute('width', that.width);
|
||||||
|
canv.setAttribute('height', that.height);
|
||||||
|
|
||||||
|
that.drawScale();
|
||||||
|
};
|
||||||
|
|
||||||
|
function onResize() {
|
||||||
|
clearTimeout(resizeTimer);
|
||||||
|
resizeTimer = setTimeout(doneResizing, 100);
|
||||||
|
};
|
||||||
|
|
||||||
|
TimeScale.prototype.onResize = onResize;
|
||||||
|
|
||||||
this.drawScale();
|
this.drawScale();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -208,11 +208,20 @@ TrackEditor.prototype.drawTrack = function(buffer) {
|
||||||
this.drawer.drawFades(this.fades);
|
this.drawer.drawFades(this.fades);
|
||||||
};
|
};
|
||||||
|
|
||||||
TrackEditor.prototype.onTrackLoad = function(buffer) {
|
TrackEditor.prototype.onTrackLoad = function(buffer, err) {
|
||||||
var res,
|
var res,
|
||||||
startTime,
|
startTime,
|
||||||
endTime;
|
endTime;
|
||||||
|
|
||||||
|
if (err !== undefined) {
|
||||||
|
this.container.innerHTML = "";
|
||||||
|
this.container.classList.add("error");
|
||||||
|
|
||||||
|
this.fire('unregister');
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (this.cues === undefined) {
|
if (this.cues === undefined) {
|
||||||
this.setCuePoints(0, buffer.length - 1);
|
this.setCuePoints(0, buffer.length - 1);
|
||||||
}
|
}
|
||||||
|
@ -282,6 +291,8 @@ TrackEditor.prototype.deactivate = function() {
|
||||||
/* start of state methods */
|
/* start of state methods */
|
||||||
|
|
||||||
TrackEditor.prototype.timeShift = function(e) {
|
TrackEditor.prototype.timeShift = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var el = e.currentTarget, //want the events placed on the channel wrapper.
|
var el = e.currentTarget, //want the events placed on the channel wrapper.
|
||||||
startX = e.pageX,
|
startX = e.pageX,
|
||||||
diffX = 0,
|
diffX = 0,
|
||||||
|
@ -296,6 +307,8 @@ TrackEditor.prototype.timeShift = function(e) {
|
||||||
|
|
||||||
//dynamically put an event on the element.
|
//dynamically put an event on the element.
|
||||||
el.onmousemove = function(e) {
|
el.onmousemove = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var endX = e.pageX;
|
var endX = e.pageX;
|
||||||
|
|
||||||
diffX = endX - startX;
|
diffX = endX - startX;
|
||||||
|
@ -303,7 +316,9 @@ TrackEditor.prototype.timeShift = function(e) {
|
||||||
editor.drawer.setTimeShift(updatedX);
|
editor.drawer.setTimeShift(updatedX);
|
||||||
editor.leftOffset = editor.pixelsToSamples(updatedX);
|
editor.leftOffset = editor.pixelsToSamples(updatedX);
|
||||||
};
|
};
|
||||||
el.onmouseup = function() {
|
el.onmouseup = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var delta;
|
var delta;
|
||||||
|
|
||||||
el.onmousemove = el.onmouseup = null;
|
el.onmousemove = el.onmouseup = null;
|
||||||
|
@ -453,6 +468,8 @@ TrackEditor.prototype.findLayerOffset = function(e) {
|
||||||
};
|
};
|
||||||
|
|
||||||
TrackEditor.prototype.selectStart = function(e) {
|
TrackEditor.prototype.selectStart = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var el = e.currentTarget, //want the events placed on the channel wrapper.
|
var el = e.currentTarget, //want the events placed on the channel wrapper.
|
||||||
editor = this,
|
editor = this,
|
||||||
startX = e.layerX || e.offsetX, //relative to e.target (want the canvas).
|
startX = e.layerX || e.offsetX, //relative to e.target (want the canvas).
|
||||||
|
@ -475,6 +492,8 @@ TrackEditor.prototype.selectStart = function(e) {
|
||||||
|
|
||||||
//dynamically put an event on the element.
|
//dynamically put an event on the element.
|
||||||
el.onmousemove = function(e) {
|
el.onmousemove = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var currentX = layerOffset + (e.layerX || e.offsetX),
|
var currentX = layerOffset + (e.layerX || e.offsetX),
|
||||||
delta = currentX - prevX,
|
delta = currentX - prevX,
|
||||||
minX = Math.min(prevX, currentX, startX),
|
minX = Math.min(prevX, currentX, startX),
|
||||||
|
@ -500,6 +519,8 @@ TrackEditor.prototype.selectStart = function(e) {
|
||||||
prevX = currentX;
|
prevX = currentX;
|
||||||
};
|
};
|
||||||
el.onmouseup = function(e) {
|
el.onmouseup = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var endX = layerOffset + (e.layerX || e.offsetX),
|
var endX = layerOffset + (e.layerX || e.offsetX),
|
||||||
minX, maxX,
|
minX, maxX,
|
||||||
startTime, endTime;
|
startTime, endTime;
|
||||||
|
@ -555,6 +576,8 @@ TrackEditor.prototype.selectCursorPos = function(e) {
|
||||||
};
|
};
|
||||||
|
|
||||||
TrackEditor.prototype.selectFadeIn = function(e) {
|
TrackEditor.prototype.selectFadeIn = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var startX = e.layerX || e.offsetX, //relative to e.target (want the canvas).
|
var startX = e.layerX || e.offsetX, //relative to e.target (want the canvas).
|
||||||
layerOffset,
|
layerOffset,
|
||||||
FADETYPE = "FadeIn",
|
FADETYPE = "FadeIn",
|
||||||
|
@ -572,6 +595,8 @@ TrackEditor.prototype.selectFadeIn = function(e) {
|
||||||
};
|
};
|
||||||
|
|
||||||
TrackEditor.prototype.selectFadeOut = function(e) {
|
TrackEditor.prototype.selectFadeOut = function(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
var startX = e.layerX || e.offsetX, //relative to e.target (want the canvas).
|
var startX = e.layerX || e.offsetX, //relative to e.target (want the canvas).
|
||||||
layerOffset,
|
layerOffset,
|
||||||
FADETYPE = "FadeOut",
|
FADETYPE = "FadeOut",
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue