variabletime/bin/web/js/record.js

190 lines
7.8 KiB
JavaScript

const Record = function(tp) {
const hot = {};
let isRecording = false;
const addRecordButton = (layer, propTitle) => {
const panel = tp.getPanel();
const panelPropTitle = tp.getPanelPropTitle(propTitle);
if (panelPropTitle !== null) {
const container = tp.getPanelPropContainer(panelPropTitle);
if (container === null) {
console.log("Record::addRecordButton",
`impossible! cannot find panelPropContainer for ${propTitle}`);
} else if (container.querySelector('.recordButton') !== null) {
// this is super verbose, let's not log by default
//console.log("Record::addRecordButton",
//`already added an record button for ${propTitle}`);
} else {
const button = document.createElement('div');
button.classList.add('recordButton');
button.classList.add(`recordButton${propTitle}`);
button.innerHTML = `<img src="/web/assets/record.svg" alt="record" />`;
container.append(button);
button.addEventListener('click', () => {
if (!hot.hasOwnProperty(layer.id())) {
hot[layer.id()] = {};
}
if (!hot[layer.id()].hasOwnProperty(propTitle)) {
hot[layer.id()][propTitle] = {
recording: [],
};
button.classList.add('active');
startRecording();
} else {
stopRecording();
delete hot[layer.id()][propTitle];
if (Object.keys(hot[layer.id()]).length === 0) {
delete hot[layer.id()];
}
button.classList.remove('active');
}
});
}
} else {
console.log("Record::addRecordButton",
`cannot find panelPropTitle for ${propTitle}`);
}
};
const cloneInput = (layer, propTitle) => {
const panel = tp.getPanel();
const panelPropTitle = tp.getPanelPropTitle(propTitle);
if (panelPropTitle !== null) {
const container = tp.getPanelPropContainer(panelPropTitle);
if (container === null) {
console.log("Record::cloneInput",
`impossible! cannot find panelPropContainer for ${propTitle}`);
} else if (container.querySelector('input.recording') !== null) {
console.log("Record::cloneInput",
`already cloned input for ${propTitle}`);
} else {
const input = container.querySelector('input');
if (input === null) {
console.log("Record::cloneInput",
`uuh.. seems there is no input to clone for ${propTitle}`);
} else {
const input_clone = input.cloneNode();
input_clone.classList.value = '';
input_clone.classList.add('recording');
input.parentNode.after(input_clone);
input.setAttribute('data-previousDisplay', input.style.display);
input.style.display = 'none';
return input_clone;
}
}
}
return null;
};
const uncloneInput = (layer, propTitle) => {
const panel = tp.getPanel();
const panelPropTitle = tp.getPanelPropTitle(propTitle);
if (panelPropTitle !== null) {
const container = tp.getPanelPropContainer(panelPropTitle);
if (container === null) {
console.log("Record::uncloneInput",
`impossible! cannot find panelPropContainer for ${propTitle}`);
} else if (container.querySelector('input.recording') === null) {
console.log("Record::uncloneInput",
`already uncloned input for ${propTitle}`);
} else {
const input = container.querySelector('input:not(.recording)');
const input_clone = container.querySelector('input.recording');
if (input === null ) {
console.log("Record::uncloneInput",
`uuh.. seems there is no input for ${propTitle}`);
} else if (input_clone === null ) {
console.log("Record::uncloneInput",
`uuh.. seems there is no input_clone for ${propTitle}`);
} else {
input_clone.remove();
input.removeAttribute('data-previousDisplay');
const previousInputDisplay = input.getAttribute('data-previousDisplay');
input.style.display = previousInputDisplay;
}
}
}
};
const injectPanel = (layer) => {
const props = Object.keys(layer.theatreObject.value);
props.forEach((propTitle) => {
if (config.record.ignoreProps.indexOf(propTitle) < 0) {
addRecordButton(layer, propTitle);
}
});
};
const startRecording = () => {
tp.sheet.sequence.pause();
const layerKeys = Object.keys(hot);
layerKeys.forEach((layerID) => {
const layer = getLayer(layerID);
layer.updateValuesViaTheatre(false);
const propTitles = Object.keys(hot[layerID]);
propTitles.forEach((propTitle) => {
// NOTE: layerID is not actually used atm
// and should be the layer anyways
const input_clone = cloneInput(layerID, propTitle);
if (input_clone !== null) {
input_clone.addEventListener('change', (e) => {
hot[layerID][propTitle].recording.push({
position: tp.sheet.sequence.position,
value: parseFloat(input_clone.value),
});
});
} else {
console.log('whoops input_clone is null');
}
});
tp.sheet.sequence.position = 0;
tp.sheet.sequence.play();
});
isRecording = true;
};
const stopRecording = () => {
console.log('stoprecording');
const layerKeys = Object.keys(hot);
console.log({layerKeys});
layerKeys.forEach((layerID) => {
console.log(layerID);
const layer = getLayer(layerID);
layer.updateValuesViaTheatre(true);
const propTitles = Object.keys(hot[layerID]);
const keyframes = [];
propTitles.forEach((propTitle) => {
console.log(propTitle);
// NOTE: layerID is not actually used atm
// and should be the layer anyways
uncloneInput(layerID, propTitle);
console.log('should have uncloned input for ' + propTitle);
keyframes.push({
path: [propTitle],
keyframes: hot[layerID][propTitle].recording,
});
});
setTimeout(() => {
console.log('adding the keyframes now because we wnat it to happen right now please');
tp.addKeyframes(layer, keyframes);
}, 2000);
});
isRecording = false;
};
// public
this.addRecordButton = addRecordButton;
this.getHot = () => {
return hot;
};
this.isRecording = () => {
return isRecording;
};
this.injectPanel = injectPanel;
this.startRecording = startRecording;
this.stopRecording = stopRecording;
};
export {
Record
}