mirror of
https://invent.kde.org/multimedia/kdenlive
synced 2025-12-08 01:09:59 +01:00
Compare commits
5 Commits
work/appim
...
refactorin
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4fc2f242e8 | ||
|
|
fb9f6c5753 | ||
|
|
b03088c3fe | ||
|
|
56060143fe | ||
|
|
e16d044b4d |
@@ -534,31 +534,35 @@ void ProjectClip::createDisabledMasterProducer()
|
|||||||
m_effectStack->addService(m_disabledProducer);
|
m_effectStack->addService(m_disabledProducer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
std::shared_ptr<Mlt::Producer> ProjectClip::getTimelineProducer(int clipId, PlaylistState::ClipState state, double speed)
|
|
||||||
|
std::shared_ptr<Mlt::Producer> ProjectClip::getTimelineProducer(int trackId, int clipId, PlaylistState::ClipState state, double speed)
|
||||||
{
|
{
|
||||||
if (!m_masterProducer) {
|
if (!m_masterProducer) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
if (qFuzzyCompare(speed, 1.0)) {
|
if (qFuzzyCompare(speed, 1.0)) {
|
||||||
// we are requesting a normal speed producer
|
// we are requesting a normal speed producer
|
||||||
// We can first cleen the speed producers we have for the current id
|
if (trackId == -1) {
|
||||||
|
// Temporary copy, return clone of master
|
||||||
|
return std::shared_ptr<Mlt::Producer>(m_masterProducer->cut());
|
||||||
|
}
|
||||||
if (m_timewarpProducers.count(clipId) > 0) {
|
if (m_timewarpProducers.count(clipId) > 0) {
|
||||||
m_effectStack->removeService(m_timewarpProducers[clipId]);
|
m_effectStack->removeService(m_timewarpProducers[clipId]);
|
||||||
m_timewarpProducers.erase(clipId);
|
m_timewarpProducers.erase(clipId);
|
||||||
}
|
}
|
||||||
if (state == PlaylistState::AudioOnly) {
|
if (state == PlaylistState::AudioOnly) {
|
||||||
// We need to get an audio producer, if none exists
|
// We need to get an audio producer, if none exists
|
||||||
if (m_audioProducers.count(clipId) == 0) {
|
if (m_audioProducers.count(trackId) == 0) {
|
||||||
m_audioProducers[clipId] = cloneProducer(true);
|
m_audioProducers[trackId] = cloneProducer(true);
|
||||||
m_audioProducers[clipId]->set("set.test_audio", 0);
|
m_audioProducers[trackId]->set("set.test_audio", 0);
|
||||||
m_audioProducers[clipId]->set("set.test_image", 1);
|
m_audioProducers[trackId]->set("set.test_image", 1);
|
||||||
m_effectStack->addService(m_audioProducers[clipId]);
|
m_effectStack->addService(m_audioProducers[trackId]);
|
||||||
}
|
}
|
||||||
return std::shared_ptr<Mlt::Producer>(m_audioProducers[clipId]->cut());
|
return std::shared_ptr<Mlt::Producer>(m_audioProducers[trackId]->cut());
|
||||||
}
|
}
|
||||||
if (m_audioProducers.count(clipId) > 0) {
|
if (m_audioProducers.count(trackId) > 0) {
|
||||||
m_effectStack->removeService(m_audioProducers[clipId]);
|
m_effectStack->removeService(m_audioProducers[trackId]);
|
||||||
m_audioProducers.erase(clipId);
|
m_audioProducers.erase(trackId);
|
||||||
}
|
}
|
||||||
if (state == PlaylistState::VideoOnly) {
|
if (state == PlaylistState::VideoOnly) {
|
||||||
// we return the video producer
|
// we return the video producer
|
||||||
@@ -567,18 +571,18 @@ std::shared_ptr<Mlt::Producer> ProjectClip::getTimelineProducer(int clipId, Play
|
|||||||
int duration = m_masterProducer->time_to_frames(m_masterProducer->get("kdenlive:duration"));
|
int duration = m_masterProducer->time_to_frames(m_masterProducer->get("kdenlive:duration"));
|
||||||
return std::shared_ptr<Mlt::Producer>(m_masterProducer->cut(-1, duration > 0 ? duration : -1));
|
return std::shared_ptr<Mlt::Producer>(m_masterProducer->cut(-1, duration > 0 ? duration : -1));
|
||||||
}
|
}
|
||||||
if (m_videoProducers.count(clipId) == 0) {
|
if (m_videoProducers.count(trackId) == 0) {
|
||||||
m_videoProducers[clipId] = cloneProducer(true);
|
m_videoProducers[trackId] = cloneProducer(true);
|
||||||
m_videoProducers[clipId]->set("set.test_audio", 1);
|
m_videoProducers[trackId]->set("set.test_audio", 1);
|
||||||
m_videoProducers[clipId]->set("set.test_image", 0);
|
m_videoProducers[trackId]->set("set.test_image", 0);
|
||||||
m_effectStack->addService(m_videoProducers[clipId]);
|
m_effectStack->addService(m_videoProducers[trackId]);
|
||||||
}
|
}
|
||||||
int duration = m_masterProducer->time_to_frames(m_masterProducer->get("kdenlive:duration"));
|
int duration = m_masterProducer->time_to_frames(m_masterProducer->get("kdenlive:duration"));
|
||||||
return std::shared_ptr<Mlt::Producer>(m_videoProducers[clipId]->cut(-1, duration > 0 ? duration : -1));
|
return std::shared_ptr<Mlt::Producer>(m_videoProducers[trackId]->cut(-1, duration > 0 ? duration : -1));
|
||||||
}
|
}
|
||||||
if (m_videoProducers.count(clipId) > 0) {
|
if (m_videoProducers.count(trackId) > 0) {
|
||||||
m_effectStack->removeService(m_videoProducers[clipId]);
|
m_effectStack->removeService(m_videoProducers[trackId]);
|
||||||
m_videoProducers.erase(clipId);
|
m_videoProducers.erase(trackId);
|
||||||
}
|
}
|
||||||
Q_ASSERT(state == PlaylistState::Disabled);
|
Q_ASSERT(state == PlaylistState::Disabled);
|
||||||
createDisabledMasterProducer();
|
createDisabledMasterProducer();
|
||||||
@@ -586,16 +590,7 @@ std::shared_ptr<Mlt::Producer> ProjectClip::getTimelineProducer(int clipId, Play
|
|||||||
return std::shared_ptr<Mlt::Producer>(m_disabledProducer->cut(-1, duration > 0 ? duration : -1));
|
return std::shared_ptr<Mlt::Producer>(m_disabledProducer->cut(-1, duration > 0 ? duration : -1));
|
||||||
}
|
}
|
||||||
|
|
||||||
// in that case, we need to create a warp producer, if we don't have one
|
// For timewarp clips, we keep one separate producer for each clip.
|
||||||
if (m_audioProducers.count(clipId) > 0) {
|
|
||||||
m_effectStack->removeService(m_audioProducers[clipId]);
|
|
||||||
m_audioProducers.erase(clipId);
|
|
||||||
}
|
|
||||||
if (m_videoProducers.count(clipId) > 0) {
|
|
||||||
m_effectStack->removeService(m_videoProducers[clipId]);
|
|
||||||
m_videoProducers.erase(clipId);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::shared_ptr<Mlt::Producer> warpProducer;
|
std::shared_ptr<Mlt::Producer> warpProducer;
|
||||||
if (m_timewarpProducers.count(clipId) > 0) {
|
if (m_timewarpProducers.count(clipId) > 0) {
|
||||||
// remove in all cases, we add it unconditionally anyways
|
// remove in all cases, we add it unconditionally anyways
|
||||||
@@ -656,7 +651,7 @@ std::pair<std::shared_ptr<Mlt::Producer>, bool> ProjectClip::giveMasterAndGetTim
|
|||||||
|
|
||||||
if (state != PlaylistState::Disabled || timeWarp) {
|
if (state != PlaylistState::Disabled || timeWarp) {
|
||||||
// In that case, we must create copies
|
// In that case, we must create copies
|
||||||
std::shared_ptr<Mlt::Producer> prod(getTimelineProducer(clipId, state, speed)->cut(in, out));
|
std::shared_ptr<Mlt::Producer> prod(getTimelineProducer(-1, clipId, state, speed)->cut(in, out));
|
||||||
return {prod, false};
|
return {prod, false};
|
||||||
}
|
}
|
||||||
if (state == PlaylistState::Disabled && !m_disabledProducer) {
|
if (state == PlaylistState::Disabled && !m_disabledProducer) {
|
||||||
@@ -704,7 +699,7 @@ std::pair<std::shared_ptr<Mlt::Producer>, bool> ProjectClip::giveMasterAndGetTim
|
|||||||
if (QString::fromUtf8(master->parent().get("mlt_service")) == QLatin1String("timewarp")) {
|
if (QString::fromUtf8(master->parent().get("mlt_service")) == QLatin1String("timewarp")) {
|
||||||
speed = master->get_double("warp_speed");
|
speed = master->get_double("warp_speed");
|
||||||
}
|
}
|
||||||
return {getTimelineProducer(clipId, state, speed), false};
|
return {getTimelineProducer(-1, clipId, state, speed), false};
|
||||||
}
|
}
|
||||||
// we have a problem
|
// we have a problem
|
||||||
return {std::shared_ptr<Mlt::Producer>(ClipController::mediaUnavailable->cut()), false};
|
return {std::shared_ptr<Mlt::Producer>(ClipController::mediaUnavailable->cut()), false};
|
||||||
|
|||||||
@@ -202,7 +202,7 @@ public:
|
|||||||
/** @brief This function returns a cut to the master producer associated to the timeline clip with given ID.
|
/** @brief This function returns a cut to the master producer associated to the timeline clip with given ID.
|
||||||
Each clip must have a different master producer (see comment of the class)
|
Each clip must have a different master producer (see comment of the class)
|
||||||
*/
|
*/
|
||||||
std::shared_ptr<Mlt::Producer> getTimelineProducer(int clipId, PlaylistState::ClipState st, double speed = 1.0);
|
std::shared_ptr<Mlt::Producer> getTimelineProducer(int trackId, int clipId, PlaylistState::ClipState st, double speed = 1.0);
|
||||||
|
|
||||||
/* @brief This function should only be used at loading. It takes a producer that was read from mlt, and checks whether the master producer is already in
|
/* @brief This function should only be used at loading. It takes a producer that was read from mlt, and checks whether the master producer is already in
|
||||||
use. If yes, then we must create a new one, because of the mixing bug. In any case, we return a cut of the master that can be used in the timeline The
|
use. If yes, then we must create a new one, because of the mixing bug. In any case, we return a cut of the master that can be used in the timeline The
|
||||||
|
|||||||
@@ -75,7 +75,7 @@ int ClipModel::construct(const std::shared_ptr<TimelineModel> &parent, const QSt
|
|||||||
videoAudio.first = videoAudio.first && binClip->hasVideo();
|
videoAudio.first = videoAudio.first && binClip->hasVideo();
|
||||||
videoAudio.second = videoAudio.second && binClip->hasAudio();
|
videoAudio.second = videoAudio.second && binClip->hasAudio();
|
||||||
state = stateFromBool(videoAudio);
|
state = stateFromBool(videoAudio);
|
||||||
std::shared_ptr<Mlt::Producer> cutProducer = binClip->getTimelineProducer(id, state, speed);
|
std::shared_ptr<Mlt::Producer> cutProducer = binClip->getTimelineProducer(-1, id, state, speed);
|
||||||
std::shared_ptr<ClipModel> clip(new ClipModel(parent, cutProducer, binClipId, id, state, speed));
|
std::shared_ptr<ClipModel> clip(new ClipModel(parent, cutProducer, binClipId, id, state, speed));
|
||||||
clip->setClipState_lambda(state)();
|
clip->setClipState_lambda(state)();
|
||||||
parent->registerClip(clip);
|
parent->registerClip(clip);
|
||||||
@@ -379,7 +379,7 @@ void ClipModel::refreshProducerFromBin(PlaylistState::ClipState state, double sp
|
|||||||
qDebug() << "changing speed" << in << out << m_speed;
|
qDebug() << "changing speed" << in << out << m_speed;
|
||||||
}
|
}
|
||||||
std::shared_ptr<ProjectClip> binClip = pCore->projectItemModel()->getClipByBinID(m_binClipId);
|
std::shared_ptr<ProjectClip> binClip = pCore->projectItemModel()->getClipByBinID(m_binClipId);
|
||||||
std::shared_ptr<Mlt::Producer> binProducer = binClip->getTimelineProducer(m_id, state, m_speed);
|
std::shared_ptr<Mlt::Producer> binProducer = binClip->getTimelineProducer(m_currentTrackId, m_id, state, m_speed);
|
||||||
m_producer = std::move(binProducer);
|
m_producer = std::move(binProducer);
|
||||||
m_producer->set_in_and_out(in, out);
|
m_producer->set_in_and_out(in, out);
|
||||||
// replant effect stack in updated service
|
// replant effect stack in updated service
|
||||||
@@ -510,6 +510,17 @@ void ClipModel::setShowKeyframes(bool show)
|
|||||||
service()->set("kdenlive:hide_keyframes", (int)!show);
|
service()->set("kdenlive:hide_keyframes", (int)!show);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ClipModel::setCurrentTrackId(int tid, bool finalMove)
|
||||||
|
{
|
||||||
|
if (tid == m_currentTrackId) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
MoveableItem::setCurrentTrackId(tid, finalMove);
|
||||||
|
if (finalMove) {
|
||||||
|
refreshProducerFromBin(m_currentState);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Fun ClipModel::setClipState_lambda(PlaylistState::ClipState state)
|
Fun ClipModel::setClipState_lambda(PlaylistState::ClipState state)
|
||||||
{
|
{
|
||||||
QWriteLocker locker(&m_lock);
|
QWriteLocker locker(&m_lock);
|
||||||
|
|||||||
@@ -157,6 +157,8 @@ protected:
|
|||||||
*/
|
*/
|
||||||
bool requestResize(int size, bool right, Fun &undo, Fun &redo, bool logUndo = true) override;
|
bool requestResize(int size, bool right, Fun &undo, Fun &redo, bool logUndo = true) override;
|
||||||
|
|
||||||
|
void setCurrentTrackId(int tid, bool finalMove = true) override;
|
||||||
|
|
||||||
/* @brief This function change the global (timeline-wise) enabled state of the effects
|
/* @brief This function change the global (timeline-wise) enabled state of the effects
|
||||||
*/
|
*/
|
||||||
void setTimelineEffectsEnabled(bool enabled);
|
void setTimelineEffectsEnabled(bool enabled);
|
||||||
|
|||||||
@@ -244,8 +244,9 @@ void CompositionModel::setInOut(int in, int out)
|
|||||||
setPosition(in);
|
setPosition(in);
|
||||||
}
|
}
|
||||||
|
|
||||||
void CompositionModel::setCurrentTrackId(int tid)
|
void CompositionModel::setCurrentTrackId(int tid, bool finalMove)
|
||||||
{
|
{
|
||||||
|
Q_UNUSED(finalMove);
|
||||||
MoveableItem::setCurrentTrackId(tid);
|
MoveableItem::setCurrentTrackId(tid);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -99,7 +99,7 @@ public:
|
|||||||
protected:
|
protected:
|
||||||
Mlt::Transition *service() const override;
|
Mlt::Transition *service() const override;
|
||||||
void setInOut(int in, int out) override;
|
void setInOut(int in, int out) override;
|
||||||
void setCurrentTrackId(int tid) override;
|
void setCurrentTrackId(int tid, bool finalMove = true) override;
|
||||||
int getOut() const override;
|
int getOut() const override;
|
||||||
int getIn() const override;
|
int getIn() const override;
|
||||||
|
|
||||||
|
|||||||
@@ -105,7 +105,7 @@ protected:
|
|||||||
If you wish to actually change the track the item, use the slot in the timeline
|
If you wish to actually change the track the item, use the slot in the timeline
|
||||||
slot.
|
slot.
|
||||||
*/
|
*/
|
||||||
virtual void setCurrentTrackId(int tid);
|
virtual void setCurrentTrackId(int tid, bool finalMove = true);
|
||||||
|
|
||||||
/* Set in and out of service */
|
/* Set in and out of service */
|
||||||
virtual void setInOut(int in, int out);
|
virtual void setInOut(int in, int out);
|
||||||
|
|||||||
@@ -81,8 +81,9 @@ template <typename Service> void MoveableItem<Service>::setPosition(int pos)
|
|||||||
m_position = pos;
|
m_position = pos;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename Service> void MoveableItem<Service>::setCurrentTrackId(int tid)
|
template <typename Service> void MoveableItem<Service>::setCurrentTrackId(int tid, bool finalMove)
|
||||||
{
|
{
|
||||||
|
Q_UNUSED(finalMove);
|
||||||
QWriteLocker locker(&m_lock);
|
QWriteLocker locker(&m_lock);
|
||||||
m_currentTrackId = tid;
|
m_currentTrackId = tid;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2682,9 +2682,9 @@ void TimelineModel::requestClipReload(int clipId)
|
|||||||
bool refreshView = oldOut > (int)binClip->frameDuration();
|
bool refreshView = oldOut > (int)binClip->frameDuration();
|
||||||
if (old_trackId != -1) {
|
if (old_trackId != -1) {
|
||||||
getTrackById(old_trackId)->requestClipDeletion(clipId, refreshView, true, local_undo, local_redo);
|
getTrackById(old_trackId)->requestClipDeletion(clipId, refreshView, true, local_undo, local_redo);
|
||||||
}
|
}
|
||||||
m_allClips[clipId]->refreshProducerFromBin();
|
|
||||||
if (old_trackId != -1) {
|
if (old_trackId != -1) {
|
||||||
|
m_allClips[clipId]->refreshProducerFromBin();
|
||||||
getTrackById(old_trackId)->requestClipInsertion(clipId, oldPos, refreshView, true, local_undo, local_redo);
|
getTrackById(old_trackId)->requestClipInsertion(clipId, oldPos, refreshView, true, local_undo, local_redo);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -134,7 +134,7 @@ Fun TrackModel::requestClipInsertion_lambda(int clipId, int position, bool updat
|
|||||||
m_allClips[clip->getId()] = clip; // store clip
|
m_allClips[clip->getId()] = clip; // store clip
|
||||||
// update clip position and track
|
// update clip position and track
|
||||||
clip->setPosition(position);
|
clip->setPosition(position);
|
||||||
clip->setCurrentTrackId(m_id);
|
clip->setCurrentTrackId(m_id, finalMove);
|
||||||
int new_in = clip->getPosition();
|
int new_in = clip->getPosition();
|
||||||
int new_out = new_in + clip->getPlaytime();
|
int new_out = new_in + clip->getPlaytime();
|
||||||
ptr->m_snaps->addPoint(new_in);
|
ptr->m_snaps->addPoint(new_in);
|
||||||
@@ -164,6 +164,7 @@ Fun TrackModel::requestClipInsertion_lambda(int clipId, int position, bool updat
|
|||||||
// Lock MLT playlist so that we don't end up with an invalid frame being displayed
|
// Lock MLT playlist so that we don't end up with an invalid frame being displayed
|
||||||
m_playlists[0].lock();
|
m_playlists[0].lock();
|
||||||
std::shared_ptr<ClipModel> clip = ptr->getClipPtr(clipId);
|
std::shared_ptr<ClipModel> clip = ptr->getClipPtr(clipId);
|
||||||
|
clip->setCurrentTrackId(m_id, finalMove);
|
||||||
int index = m_playlists[0].insert_at(position, *clip, 1);
|
int index = m_playlists[0].insert_at(position, *clip, 1);
|
||||||
m_playlists[0].consolidate_blanks();
|
m_playlists[0].consolidate_blanks();
|
||||||
m_playlists[0].unlock();
|
m_playlists[0].unlock();
|
||||||
@@ -189,6 +190,7 @@ Fun TrackModel::requestClipInsertion_lambda(int clipId, int position, bool updat
|
|||||||
// Lock MLT playlist so that we don't end up with an invalid frame being displayed
|
// Lock MLT playlist so that we don't end up with an invalid frame being displayed
|
||||||
m_playlists[0].lock();
|
m_playlists[0].lock();
|
||||||
std::shared_ptr<ClipModel> clip = ptr->getClipPtr(clipId);
|
std::shared_ptr<ClipModel> clip = ptr->getClipPtr(clipId);
|
||||||
|
clip->setCurrentTrackId(m_id);
|
||||||
int index = m_playlists[0].insert_at(position, *clip, 1);
|
int index = m_playlists[0].insert_at(position, *clip, 1);
|
||||||
m_playlists[0].consolidate_blanks();
|
m_playlists[0].consolidate_blanks();
|
||||||
m_playlists[0].unlock();
|
m_playlists[0].unlock();
|
||||||
|
|||||||
Reference in New Issue
Block a user