Hi,
just a small update that replaces my last patch... :-)
With "/chapters/interval"<0 one now can also specify the total number of the
intervals (i.e. chapters) instead of their length (>0) and there is a new
settings variable "/chapters/minimum" to specify the minimal length of a
chapter (in frames).
The last one is useful, when a fixed total number of chapters would give to
short chapters, but also to avoid creating a chapter 1min before the end of
the movie when working with a fixed chapter length.
ciao
Ralph
diff -Naur svn/ChangeLog r110-autochapter/ChangeLog > r110-autochapter.diff
--- svn/ChangeLog 2007-12-15 17:43:14.000000000 +0100
+++ r110-autochapter/ChangeLog 2007-12-30 20:57:51.000000000 +0100
@@ -1,3 +1,13 @@
+2008-01-06 Ralph Glasstetter <[EMAIL PROTECTED]> (mr)
+
+ * src/dvbcutbase.ui
+ * src/dvbcut.cpp
+ * src/dvbcut.h
+ * src/settings.cpp
+ * src/settings.h
+ Automated setting of equidistant chapter markers
+ Fixed bug concerning positioning via output frames
+
2007-12-12 Ralph Glasstetter <[EMAIL PROTECTED]> (mr)
* src/dvbcutbase.ui:
diff -Naur svn/src/dvbcutbase.ui r110-autochapter/src/dvbcutbase.ui
--- svn/src/dvbcutbase.ui 2007-12-15 17:43:14.000000000 +0100
+++ r110-autochapter/src/dvbcutbase.ui 2007-12-30 14:33:53.000000000 +0100
@@ -376,6 +376,7 @@
<action name="editChapterAction"/>
<action name="editBookmarkAction"/>
<separator/>
+ <action name="editAutoChaptersAction"/>
<action name="editSuggestAction"/>
<action name="editImportAction"/>
</item>
@@ -653,6 +654,20 @@
</action>
<action>
<property name="name">
+ <cstring>editAutoChaptersAction</cstring>
+ </property>
+ <property name="enabled">
+ <bool>false</bool>
+ </property>
+ <property name="text">
+ <string>Auto chapters</string>
+ </property>
+ <property name="accel">
+ <string>Ctrl+C</string>
+ </property>
+ </action>
+ <action>
+ <property name="name">
<cstring>editSuggestAction</cstring>
</property>
<property name="enabled">
@@ -926,6 +941,12 @@
<slot>editBookmark()</slot>
</connection>
<connection>
+ <sender>editAutoChaptersAction</sender>
+ <signal>activated()</signal>
+ <receiver>dvbcutbase</receiver>
+ <slot>editAutoChapters()</slot>
+ </connection>
+ <connection>
<sender>editSuggestAction</sender>
<signal>activated()</signal>
<receiver>dvbcutbase</receiver>
@@ -1082,6 +1103,7 @@
<slot>editStop()</slot>
<slot>editChapter()</slot>
<slot>editBookmark()</slot>
+ <slot>editAutoChapters()</slot>
<slot>editSuggest()</slot>
<slot>editImport()</slot>
<slot>editConvert(int)</slot>
diff -Naur svn/src/dvbcut.cpp r110-autochapter/src/dvbcut.cpp
--- svn/src/dvbcut.cpp 2007-12-15 17:43:14.000000000 +0100
+++ r110-autochapter/src/dvbcut.cpp 2008-01-06 23:06:24.000000000 +0100
@@ -148,7 +148,7 @@
connect( recentfilespopup, SIGNAL( aboutToShow() ), this, SLOT( abouttoshowrecentfiles() ) );
editconvertpopup=new QPopupMenu(this);
- editMenu->insertItem(QString("Convert bookmarks"),editconvertpopup,-1,7);
+ editMenu->insertItem(QString("Convert bookmarks"),editconvertpopup,-1,8);
connect( editconvertpopup, SIGNAL( activated(int) ), this, SLOT( editConvert(int) ) );
connect( editconvertpopup, SIGNAL( aboutToShow() ), this, SLOT( abouttoshoweditconvert() ) );
@@ -854,6 +854,82 @@
update_quick_picture_lookup_table();
}
+void dvbcut::editAutoChapters()
+{
+ int inpic, chapters = 0;
+ quick_picture_lookup_t::iterator it;
+ QImage p1, p2;
+
+ // the first chapter at 0sec is ALWAYS set by default from update_quick_picture_lookup_table()
+ int chapter_start;
+ if(settings().chapter_interval>0) {
+ chapter_start = settings().chapter_interval; // fixed length of intervals
+ } else {
+ chapter_start = quick_picture_lookup.back().outpicture/(1-settings().chapter_interval); // given number of chapters
+ chapter_start = chapter_start > settings().chapter_minimum ? chapter_start : settings().chapter_minimum;
+ }
+ // don't make a new chapter if it would be shorter than the specified minimal length
+ int chapter_max = quick_picture_lookup.back().outpicture - settings().chapter_minimum;
+
+ for(int outpic = chapter_start; outpic < chapter_max; outpic+=chapter_start)
+ if (!quick_picture_lookup.empty()) {
+ // find the entry in the quick_picture_lookup table that corresponds to given output picture
+ it = std::upper_bound(quick_picture_lookup.begin(),quick_picture_lookup.end(),outpic,quick_picture_lookup_s::cmp_outpicture());
+ inpic = outpic - it->outpicture + it->stoppicture;
+
+ if(inpic+settings().chapter_tolerance>it->stoppicture) {
+ if(it == quick_picture_lookup.end()) break;
+ // take begin of next START/STOP range as chapter picture if to near at end of current range
+ it++;
+ inpic=it->startpicture;
+ } else if(settings().chapter_tolerance>0) {
+ // look for the next scene change inside specified frame tolerance (VERY SLOW!!!)
+ if (!imgp)
+ imgp = new imageprovider(*mpg, new dvbcutbusy(this), false, viewscalefactor, settings().chapter_tolerance);
+ p2 = imgp->getimage(inpic,fine);
+ for(int pic=inpic+1; pic<inpic+settings().chapter_tolerance && pic<pictures; pic++) {
+ // get next picture
+ p1 = p2;
+ p2 = imgp->getimage(pic,fine);
+ if (p2.size()!=p1.size())
+ p2=p2.scale(p1.size());
+
+ // calculate color distance between two consecutive frames
+ double dist=0.;
+ if (p2.depth()==32 && p1.depth()==32)
+ for (int y=0;y<p1.height();++y) {
+ QRgb *col1=(QRgb*)p1.scanLine(y);
+ QRgb *col2=(QRgb*)p2.scanLine(y);
+
+ for (int x=p1.width();x>0;--x) {
+ dist+=sqrt(pow(qRed(*col1)-qRed(*col2),2)+pow(qGreen(*col1)-qGreen(*col2),2)+pow(qBlue(*col1)-qBlue(*col2),2));
+ // that's a bit faster...
+ //dist+=(abs(qRed(*col1)-qRed(*col2))+abs(qGreen(*col1)-qGreen(*col2))+abs(qBlue(*col1)-qBlue(*col2)));
+ ++col1;
+ ++col2;
+ }
+ }
+ dist/=(p1.height()*p1.width());
+
+ // 50. seems to be a good measure for the color distance at scene changes (about sqrt(3)*50. if sum of abs values)!
+ //fprintf(stderr,"%d, DIST=%f\n",pic,dist);
+ if(dist>settings().chapter_threshold) {
+ inpic=pic;
+ statusBar()->message(QString().sprintf("%d. Scene change @ %d, DIST=%f\n",chapters+1,inpic,dist));
+ break;
+ }
+ }
+ }
+
+ addEventListItem(inpic, EventListItem::chapter);
+ chapters++;
+ }
+
+ if (chapters)
+ update_quick_picture_lookup_table();
+
+}
+
void dvbcut::editSuggest()
{
int pic = 0, found=0;
@@ -1366,7 +1442,6 @@
// find the entry in the quick_picture_lookup table that corresponds to given output picture
quick_picture_lookup_t::iterator it=
std::upper_bound(quick_picture_lookup.begin(),quick_picture_lookup.end(),outpic,quick_picture_lookup_s::cmp_outpicture());
- --it;
inpic=outpic-it->outpicture+it->stoppicture;
fine=true;
linslider->setValue(inpic);
@@ -1600,6 +1675,7 @@
editStopAction->setEnabled(false);
editChapterAction->setEnabled(false);
editBookmarkAction->setEnabled(false);
+ editAutoChaptersAction->setEnabled(false);
editSuggestAction->setEnabled(false);
editImportAction->setEnabled(false);
//editConvertAction->setEnabled(false);
@@ -1931,6 +2007,7 @@
editStopAction->setEnabled(true);
editChapterAction->setEnabled(true);
editBookmarkAction->setEnabled(true);
+ editAutoChaptersAction->setEnabled(true);
editSuggestAction->setEnabled(true);
editImportAction->setEnabled(true);
//editConvertAction->setEnabled(true);
diff -Naur svn/src/dvbcut.h r110-autochapter/src/dvbcut.h
--- svn/src/dvbcut.h 2007-12-15 17:43:14.000000000 +0100
+++ r110-autochapter/src/dvbcut.h 2007-12-30 14:32:57.000000000 +0100
@@ -153,6 +153,7 @@
virtual void editChapter();
virtual void editStop();
virtual void editStart();
+ virtual void editAutoChapters();
virtual void editSuggest();
virtual void editImport();
virtual void editConvert(int);
diff -Naur svn/src/settings.cpp r110-autochapter/src/settings.cpp
--- svn/src/settings.cpp 2007-12-12 11:14:15.000000000 +0100
+++ r110-autochapter/src/settings.cpp 2008-01-06 23:05:18.000000000 +0100
@@ -58,13 +58,25 @@
#define DVBCUT_DEFAULT_PIPE_LABEL \
"DVD-Video titleset (dvdauthor)"
#define DVBCUT_DEFAULT_PIPE_FORMAT (0)
-/* ok,... for time consuming conversions one does not save any time processing the piped output... but just as an example. ;-)
-#define DVBCUT_DEFAULT_PIPE_COMMAND \
- "|ffmpeg -f mpeg2video -i - -f avi -vcodec mpeg4 -b 1200k -g 250 -bf 2 -acodec libmp3lame -ab 128k -ar 44100 %OUTPUT%"
-#define DVBCUT_DEFAULT_PIPE_POST ""
-#define DVBCUT_DEFAULT_PIPE_LABEL \
- "MPEG-4/ASP (ffmpeg)"
-#define DVBCUT_DEFAULT_PIPE_FORMAT (1)
+/*
+// SOME OTHER EXAMPLES for the settings file ~/.qt/dvbcut.sf.netrc
+// (ok, for time consuming conversions one does not save any time, but it may be convenient...)
+// 1. Conversion to mpeg4 avi-file with ffmpeg:
+// (to recode to a smaller MPEG2 File use "--target dvd -acodec copy"?)!
+pipe/1/command=|ffmpeg -f mpeg2video -i - -f avi -vcodec mpeg4 -b 1200k -g 250 -bf 2 -acodec libmp3lame -ab 128k -ar 44100 %OUTPUT%
+pipe/1/format=1
+pipe/1/label=MPEG-4/ASP (ffmpeg)
+pipe/1/post=
+// 2. Shrinking with vamps by 20%, before piping to dvdauthor:
+pipe/2/command=| vamps -E 1.2 -S 10000000000 -a 1,2,3 | dvdauthor -t -c '%CHAPTERS%' -v mpeg2 -o %OUTPUT% -
+pipe/2/format=0
+pipe/2/label=20% shrinked DVD-Video titleset (vamps & dvdauthor)
+pipe/2/post=dvdauthor -o %OUTPUT% -T
+// 3. recoding to a (smaller?) MPEG2 file with DVD compliant resolution (ca. 3000kbps):
+pipe/3/command=|ffmpeg -f mpeg2video -i - --target dvd -qscale 3.0 -bf 2 -acodec copy %OUTPUT%"
+pipe/3/format=1
+pipe/3/label=recoded DVD compliant video (ffmpeg)
+pipe/3/post=
*/
dvbcut_settings::dvbcut_settings() {
@@ -189,6 +201,18 @@
endGroup(); // key
}
endGroup(); // pipe
+ beginGroup("/chapters");
+ // length (>0) or number (<0) of chapter(s)
+ chapter_interval = readNumEntry("/interval", 600*25);
+ // detection of scene changes is rather time comsuming...
+ //chapter_tolerance = readNumEntry("/tolerance", 10*25);
+ //... better switch it off per default!
+ chapter_tolerance = readNumEntry("/tolerance", 0);
+ // average color distance needed for a scene change
+ chapter_threshold = readDoubleEntry("/threshold", 50.);
+ // minimal length of a chapter
+ chapter_minimum = readNumEntry("/minimum", 200*25);
+ endGroup(); // auto chapters
}
void
@@ -266,6 +290,12 @@
endGroup(); // key
}
endGroup(); // pipe
+ beginGroup("/chapters");
+ writeEntry("/interval", chapter_interval);
+ writeEntry("/tolerance", chapter_tolerance);
+ writeEntry("/threshold", chapter_threshold);
+ writeEntry("/minimum", chapter_minimum);
+ endGroup(); // auto chapters
}
// private settings variable
diff -Naur svn/src/settings.h r110-autochapter/src/settings.h
--- svn/src/settings.h 2007-12-08 12:11:13.000000000 +0100
+++ r110-autochapter/src/settings.h 2008-01-06 18:49:50.000000000 +0100
@@ -79,6 +79,10 @@
std::vector<QString> pipe_post;
std::vector<QString> pipe_label;
std::vector<int> pipe_format;
+ int chapter_interval;
+ int chapter_tolerance;
+ double chapter_threshold;
+ int chapter_minimum;
};
-------------------------------------------------------------------------
This SF.net email is sponsored by: Microsoft
Defy all challenges. Microsoft(R) Visual Studio 2005.
http://clk.atdmt.com/MRT/go/vse0120000070mrt/direct/01/
_______________________________________________
DVBCUT-user mailing list
DVBCUT-user@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/dvbcut-user