Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
Multimedia
Kdenlive
Commits
3c0a8db4
Commit
3c0a8db4
authored
Sep 12, 2020
by
Jean-Baptiste Mardelle
Browse files
Correctly load same track transitions when opening project
parent
f371478a
Changes
7
Hide whitespace changes
Inline
Side-by-side
src/timeline2/model/builders/meltBuilder.cpp
View file @
3c0a8db4
...
...
@@ -39,6 +39,7 @@
#include <mlt++/MltProducer.h>
#include <mlt++/MltProfile.h>
#include <mlt++/MltFilter.h>
#include <mlt++/MltField.h>
#include <mlt++/MltTransition.h>
#include <QApplication>
...
...
@@ -47,7 +48,7 @@ static QStringList m_errorMessage;
bool
constructTrackFromMelt
(
const
std
::
shared_ptr
<
TimelineItemModel
>
&
timeline
,
int
tid
,
Mlt
::
Tractor
&
track
,
const
std
::
unordered_map
<
QString
,
QString
>
&
binIdCorresp
,
Fun
&
undo
,
Fun
&
redo
,
bool
audioTrack
,
QString
originalDecimalPoint
,
QProgressDialog
*
progressDialog
=
nullptr
);
bool
constructTrackFromMelt
(
const
std
::
shared_ptr
<
TimelineItemModel
>
&
timeline
,
int
tid
,
Mlt
::
Playlist
&
track
,
const
std
::
unordered_map
<
QString
,
QString
>
&
binIdCorresp
,
Fun
&
undo
,
Fun
&
redo
,
bool
audioTrack
,
QString
originalDecimalPoint
,
QProgressDialog
*
progressDialog
=
nullptr
);
const
std
::
unordered_map
<
QString
,
QString
>
&
binIdCorresp
,
Fun
&
undo
,
Fun
&
redo
,
bool
audioTrack
,
QString
originalDecimalPoint
,
int
playlist
,
QMap
<
int
,
int
>
mixList
,
QProgressDialog
*
progressDialog
=
nullptr
);
bool
constructTimelineFromMelt
(
const
std
::
shared_ptr
<
TimelineItemModel
>
&
timeline
,
Mlt
::
Tractor
tractor
,
QProgressDialog
*
progressDialog
,
QString
originalDecimalPoint
)
{
...
...
@@ -127,7 +128,7 @@ bool constructTimelineFromMelt(const std::shared_ptr<TimelineItemModel> &timelin
timeline
->
setTrackProperty
(
tid
,
QStringLiteral
(
"hide"
),
QString
::
number
(
muteState
));
}
ok
=
ok
&&
constructTrackFromMelt
(
timeline
,
tid
,
local_playlist
,
binIdCorresp
,
undo
,
redo
,
audioTrack
,
originalDecimalPoint
,
progressDialog
);
ok
=
ok
&&
constructTrackFromMelt
(
timeline
,
tid
,
local_playlist
,
binIdCorresp
,
undo
,
redo
,
audioTrack
,
originalDecimalPoint
,
0
,
{},
progressDialog
);
if
(
local_playlist
.
get_int
(
"kdenlive:locked_track"
)
>
0
)
{
lockedTracksIndexes
<<
tid
;
}
...
...
@@ -221,6 +222,23 @@ bool constructTrackFromMelt(const std::shared_ptr<TimelineItemModel> &timeline,
qDebug
()
<<
"ERROR : wrong number of subtracks"
;
return
false
;
}
// Check same track transitions
QScopedPointer
<
Mlt
::
Service
>
service
(
track
.
field
());
QList
<
Mlt
::
Transition
*>
compositions
;
QMap
<
int
,
int
>
mixList
;
while
((
service
!=
nullptr
)
&&
service
->
is_valid
())
{
if
(
service
->
type
()
==
transition_type
)
{
Mlt
::
Transition
t
((
mlt_transition
)
service
->
get_service
());
mixList
.
insert
(
t
.
get_in
(),
t
.
get_out
());
QString
id
(
t
.
get
(
"kdenlive_id"
));
compositions
<<
new
Mlt
::
Transition
(
t
);
if
(
id
.
isEmpty
())
{
qDebug
()
<<
"// Warning, this should not happen, transition without id: "
<<
t
.
get
(
"id"
)
<<
" = "
<<
t
.
get
(
"mlt_service"
);
t
.
set
(
"kdenlive_id"
,
t
.
get
(
"mlt_service"
));
}
}
service
.
reset
(
service
->
producer
());
}
for
(
int
i
=
0
;
i
<
track
.
count
();
i
++
)
{
std
::
unique_ptr
<
Mlt
::
Producer
>
sub_track
(
track
.
track
(
i
));
if
(
sub_track
->
type
()
!=
playlist_type
)
{
...
...
@@ -228,7 +246,7 @@ bool constructTrackFromMelt(const std::shared_ptr<TimelineItemModel> &timeline,
return
false
;
}
Mlt
::
Playlist
playlist
(
*
sub_track
);
constructTrackFromMelt
(
timeline
,
tid
,
playlist
,
binIdCorresp
,
undo
,
redo
,
audioTrack
,
originalDecimalPoint
,
progressDialog
);
constructTrackFromMelt
(
timeline
,
tid
,
playlist
,
binIdCorresp
,
undo
,
redo
,
audioTrack
,
originalDecimalPoint
,
i
,
mixList
,
progressDialog
);
if
(
i
==
0
)
{
// Pass track properties
int
height
=
track
.
get_int
(
"kdenlive:trackheight"
);
...
...
@@ -252,6 +270,9 @@ bool constructTrackFromMelt(const std::shared_ptr<TimelineItemModel> &timeline,
}
}
}
for
(
auto
compo
:
compositions
)
{
timeline
->
plantMix
(
tid
,
*
compo
);
}
std
::
shared_ptr
<
Mlt
::
Service
>
serv
=
std
::
make_shared
<
Mlt
::
Service
>
(
track
.
get_service
());
timeline
->
importTrackEffects
(
tid
,
serv
);
return
true
;
...
...
@@ -289,9 +310,10 @@ PlaylistState::ClipState inferState(const std::shared_ptr<Mlt::Producer> &prod,
}
// namespace
bool
constructTrackFromMelt
(
const
std
::
shared_ptr
<
TimelineItemModel
>
&
timeline
,
int
tid
,
Mlt
::
Playlist
&
track
,
const
std
::
unordered_map
<
QString
,
QString
>
&
binIdCorresp
,
Fun
&
undo
,
Fun
&
redo
,
bool
audioTrack
,
QString
originalDecimalPoint
,
QProgressDialog
*
progressDialog
)
const
std
::
unordered_map
<
QString
,
QString
>
&
binIdCorresp
,
Fun
&
undo
,
Fun
&
redo
,
bool
audioTrack
,
QString
originalDecimalPoint
,
int
playlist
,
QMap
<
int
,
int
>
mixList
,
QProgressDialog
*
progressDialog
)
{
int
max
=
track
.
count
();
qDebug
()
<<
"=====GOT MIXLIST FOR TID:
\n
"
<<
mixList
<<
"
\n\n
______________________________________________________"
;
for
(
int
i
=
0
;
i
<
max
;
i
++
)
{
if
(
track
.
is_blank
(
i
))
{
continue
;
...
...
@@ -341,7 +363,13 @@ bool constructTrackFromMelt(const std::shared_ptr<TimelineItemModel> &timeline,
int
cid
=
-
1
;
if
(
pCore
->
bin
()
->
getBinClip
(
binId
))
{
PlaylistState
::
ClipState
st
=
inferState
(
clip
,
audioTrack
);
cid
=
ClipModel
::
construct
(
timeline
,
binId
,
clip
,
st
,
tid
,
originalDecimalPoint
);
qDebug
()
<<
"==== INSERTING CLIP IN PLAYLIST: "
<<
playlist
<<
"
\n
8888888888888888888888"
;
int
mixDuration
=
0
;
if
(
mixList
.
contains
(
position
))
{
// Clip has a mix
mixDuration
=
mixList
.
value
(
position
)
-
position
;
}
cid
=
ClipModel
::
construct
(
timeline
,
binId
,
clip
,
st
,
tid
,
originalDecimalPoint
,
playlist
,
mixDuration
);
ok
=
timeline
->
requestClipMove
(
cid
,
tid
,
position
,
true
,
true
,
false
,
true
,
undo
,
redo
);
}
else
{
qDebug
()
<<
"// Cannot find bin clip: "
<<
binId
<<
" - "
<<
clip
->
get
(
"id"
);
...
...
src/timeline2/model/clipmodel.cpp
View file @
3c0a8db4
...
...
@@ -101,7 +101,7 @@ void ClipModel::allSnaps(std::vector<int> &snaps, int offset)
}
int
ClipModel
::
construct
(
const
std
::
shared_ptr
<
TimelineModel
>
&
parent
,
const
QString
&
binClipId
,
const
std
::
shared_ptr
<
Mlt
::
Producer
>
&
producer
,
PlaylistState
::
ClipState
state
,
int
tid
,
QString
originalDecimalPoint
)
PlaylistState
::
ClipState
state
,
int
tid
,
QString
originalDecimalPoint
,
int
playlist
,
int
mixDuration
)
{
// we hand the producer to the bin clip, and in return we get a cut to a good master producer
...
...
@@ -129,6 +129,8 @@ int ClipModel::construct(const std::shared_ptr<TimelineModel> &parent, const QSt
result
.
first
->
parent
().
set
(
"warp_pitch"
,
1
);
}
clip
->
setClipState_lambda
(
state
)();
clip
->
setSubPlaylistIndex
(
playlist
);
clip
->
setMixDuration
(
mixDuration
);
parent
->
registerClip
(
clip
);
clip
->
m_effectStack
->
importEffects
(
producer
,
state
,
result
.
second
,
originalDecimalPoint
);
clip
->
m_clipMarkerModel
->
setReferenceModel
(
binClip
->
getMarkerModel
(),
speed
);
...
...
src/timeline2/model/clipmodel.hpp
View file @
3c0a8db4
...
...
@@ -65,7 +65,7 @@ public:
Note that there is no guarantee that this producer is actually going to be used. It might be discarded.
*/
static
int
construct
(
const
std
::
shared_ptr
<
TimelineModel
>
&
parent
,
const
QString
&
binClipId
,
const
std
::
shared_ptr
<
Mlt
::
Producer
>
&
producer
,
PlaylistState
::
ClipState
state
,
int
tid
,
QString
originalDecimalPoint
);
PlaylistState
::
ClipState
state
,
int
tid
,
QString
originalDecimalPoint
,
int
playlist
=
0
,
int
mixDuration
=
0
);
/** @brief returns a property of the clip, or from it's parent if it's a cut
*/
...
...
src/timeline2/model/timelinemodel.cpp
View file @
3c0a8db4
...
...
@@ -654,16 +654,6 @@ bool TimelineModel::requestClipMove(int clipId, int trackId, int position, bool
std
::
pair
<
MixInfo
,
MixInfo
>
mixData
=
getTrackById_const
(
old_trackId
)
->
getMixInfo
(
clipId
);
if
(
mixData
.
first
.
firstClipId
>
-
1
)
{
// We have a mix at clip start
bool
mixGroupMove
=
false
;
if
(
m_groups
->
isInGroup
(
clipId
))
{
int
parentGroup
=
m_groups
->
getRootId
(
clipId
);
if
(
parentGroup
>
-
1
)
{
std
::
unordered_set
<
int
>
sub
=
m_groups
->
getLeaves
(
parentGroup
);
if
(
sub
.
count
(
mixData
.
first
.
firstClipId
)
>
0
&&
sub
.
count
(
mixData
.
first
.
secondClipId
)
>
0
)
{
mixGroupMove
=
true
;
}
}
}
sync_mix
=
[
this
,
old_trackId
,
finalMove
]()
{
getTrackById_const
(
old_trackId
)
->
syncronizeMixes
(
finalMove
);
return
true
;
...
...
@@ -4504,3 +4494,9 @@ void TimelineModel::switchComposition(int cid, const QString &compoId)
undo
();
}
}
void
TimelineModel
::
plantMix
(
int
tid
,
Mlt
::
Transition
&
t
)
{
getTrackById_const
(
tid
)
->
getTrackService
()
->
plant_transition
(
t
,
0
,
1
);
getTrackById_const
(
tid
)
->
loadMix
(
t
);
}
src/timeline2/model/timelinemodel.hpp
View file @
3c0a8db4
...
...
@@ -417,6 +417,9 @@ public:
* @param compoId the name of the new composition we want to insert
*/
void
switchComposition
(
int
cid
,
const
QString
&
compoId
);
/** @brief Plant a same track composition in track tid
*/
void
plantMix
(
int
tid
,
Mlt
::
Transition
&
t
);
protected:
/* @brief Creates a new clip instance without inserting it.
...
...
src/timeline2/model/trackmodel.cpp
View file @
3c0a8db4
...
...
@@ -1706,3 +1706,16 @@ bool TrackModel::hasMix(int cid) const
}
return
false
;
}
bool
TrackModel
::
loadMix
(
Mlt
::
Transition
&
t
)
{
//TODO: manage case where both mix clips would start at same position
int
in
=
t
.
get_in
();
int
out
=
t
.
get_out
();
int
cid1
=
getClipByPosition
(
in
);
int
cid2
=
getClipByPosition
(
out
);
std
::
shared_ptr
<
Mlt
::
Transition
>
tr
(
&
t
);
m_sameCompositions
[
cid2
]
=
tr
;
m_mixList
.
insert
(
cid1
,
cid2
);
return
true
;
}
src/timeline2/model/trackmodel.hpp
View file @
3c0a8db4
...
...
@@ -132,6 +132,8 @@ public:
void
syncronizeMixes
(
bool
finalMove
);
/** @brief Switch a clip from one playlist to the other */
bool
switchPlaylist
(
int
clipId
,
int
position
,
int
playlist
);
/** @brief Load a same track transition from project */
bool
loadMix
(
Mlt
::
Transition
&
t
);
protected:
/* @brief This will lock the track: it will no longer allow insertion/deletion/resize of items
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment