MythTV  master
FrameAnalyzer.cpp
Go to the documentation of this file.
1 #include "mythlogging.h"
2 #include "CommDetector2.h"
3 #include "FrameAnalyzer.h"
4 
5 using namespace commDetector2;
6 
7 namespace frameAnalyzer {
8 
9 bool
10 rrccinrect(int rr, int cc, int rrow, int rcol, int rwidth, int rheight)
11 {
12  return rr >= rrow && cc >= rcol &&
13  rr < rrow + rheight && cc < rcol + rwidth;
14 }
15 
16 void
18  const char *comment)
19 {
20  for (FrameAnalyzer::FrameMap::const_iterator ii = frameMap->begin();
21  ii != frameMap->end();
22  ++ii)
23  {
24  /*
25  * QMap'd as 0-based index, but display as 1-based index to match "Edit
26  * Recording" OSD.
27  */
28  long long bb = ii.key() + 1;
29  if (*ii)
30  {
31  long long ee = bb + *ii;
32  long long len = ee - bb;
33 
34  LOG(VB_COMMFLAG, LOG_INFO, QString("%1: %2-%3 (%4-%5, %6)")
35  .arg(comment)
36  .arg(bb, 6).arg(ee - 1, 6)
37  .arg(frameToTimestamp(bb, fps))
38  .arg(frameToTimestamp(ee - 1, fps))
39  .arg(frameToTimestamp(len, fps)));
40  }
41  else
42  {
43  LOG(VB_COMMFLAG, LOG_INFO, QString("%1: %2 (%3)")
44  .arg(comment)
45  .arg(bb, 6)
46  .arg(frameToTimestamp(bb, fps)));
47  }
48  }
49 }
50 
51 void
53  const char *comment)
54 {
55  for (FrameAnalyzer::FrameMap::const_iterator ii = frameMap->begin();
56  ii != frameMap->end();
57  ++ii)
58  {
59  /*
60  * QMap'd as 0-based index, but display as 1-based index to match "Edit
61  * Recording" OSD.
62  */
63  long long bb = ii.key() + 1;
64  if (*ii)
65  {
66  long long ee = bb + *ii;
67  long long len = ee - bb;
68 
69  LOG(VB_COMMFLAG, LOG_INFO, QString("%1: %2-%3 (%4-%5, %6)")
70  .arg(comment)
71  .arg(bb, 6).arg(ee - 1, 6)
72  .arg(frameToTimestamp(bb, fps))
73  .arg(frameToTimestamp(ee - 1, fps))
74  .arg(frameToTimestampms(len, fps)));
75  }
76  else
77  {
78  LOG(VB_COMMFLAG, LOG_INFO, QString("%1: %2 (%3)")
79  .arg(comment)
80  .arg(bb, 6)
81  .arg(frameToTimestamp(bb, fps)));
82  }
83  }
84 }
85 
86 long long
88 {
89  return std::accumulate(frameMap->cbegin(), frameMap->cend(),
90  static_cast<long long>(0));
91 }
92 
93 bool
94 removeShortBreaks(FrameAnalyzer::FrameMap *breakMap, float fps, int minbreaklen,
95  bool verbose)
96 {
97  /*
98  * Remove any breaks that are less than "minbreaklen" units long.
99  *
100  * Return whether or not any breaks were actually removed.
101  */
102  FrameAnalyzer::FrameMap::Iterator bb;
103 
104  bool removed = false;
105 
106  /* Don't remove the initial commercial break, no matter how short. */
107  bb = breakMap->begin();
108  if (bb != breakMap->end() && bb.key() == 0)
109  ++bb;
110  while (bb != breakMap->end())
111  {
112  if (*bb >= minbreaklen)
113  {
114  ++bb;
115  continue;
116  }
117 
118  /* Don't remove the final commercial break, no matter how short. */
119  FrameAnalyzer::FrameMap::Iterator bb1 = bb;
120  ++bb;
121  if (bb == breakMap->end())
122  continue;
123 
124  if (verbose)
125  {
126  long long start = bb1.key();
127  long long end = start + *bb1 - 1;
128  LOG(VB_COMMFLAG, LOG_INFO, QString("Removing break %1-%2 (%3-%4)")
129  .arg(frameToTimestamp(start, fps))
130  .arg(frameToTimestamp(end, fps))
131  .arg(start + 1).arg(end + 1));
132  }
133  breakMap->erase(bb1);
134  removed = true;
135  }
136 
137  return removed;
138 }
139 
140 bool
141 removeShortSegments(FrameAnalyzer::FrameMap *breakMap, long long nframes,
142  float fps, int minseglen, bool verbose)
143 {
144  /*
145  * Remove any segments that are less than "minseglen" units long.
146  *
147  * Return whether or not any segments were actually removed.
148  */
149  FrameAnalyzer::FrameMap::Iterator bb;
150  FrameAnalyzer::FrameMap::Iterator bbnext;
151 
152  bool removed = false;
153 
154  for (bb = breakMap->begin(); bb != breakMap->end(); bb = bbnext)
155  {
156  /* Never remove initial segment (beginning at frame 0). */
157  if (bb == breakMap->begin() && bb != breakMap->end() &&
158  bb.key() != 0 && bb.key() < minseglen)
159  ++bb;
160 
161  bbnext = bb;
162  ++bbnext;
163  long long brkb = bb.key();
164  long long segb = brkb + *bb;
165  long long sege = bbnext == breakMap->end() ? nframes : bbnext.key();
166  long long seglen = sege - segb;
167  if (seglen >= minseglen)
168  continue;
169 
170  /* Merge break with next break. */
171  if (bbnext == breakMap->end())
172  {
173  if (segb != nframes)
174  {
175  /* Extend break "bb" to end of recording. */
176  if (verbose)
177  {
178  long long old1 = brkb;
179  long long old2 = segb - 1;
180  long long new1 = brkb;
181  long long new2 = nframes - 1;
182  LOG(VB_COMMFLAG, LOG_INFO,
183  QString("Removing segment %1-%2 (%3-%4)")
184  .arg(frameToTimestamp(segb + 1, fps))
185  .arg(frameToTimestamp(sege + 1, fps))
186  .arg(segb + 1).arg(sege + 1));
187  LOG(VB_COMMFLAG, LOG_INFO,
188  QString("Replacing break %1-%2 (%3-%4)"
189  " with %5-%6 (%7-%8, EOF)")
190  .arg(frameToTimestamp(old1 + 1, fps))
191  .arg(frameToTimestamp(old2 + 1, fps))
192  .arg(old1 + 1).arg(old2 + 1)
193  .arg(frameToTimestamp(new1 + 1, fps))
194  .arg(frameToTimestamp(new2 + 1, fps))
195  .arg(new1 + 1).arg(new2 + 1));
196  }
197  breakMap->remove(brkb);
198  breakMap->insert(brkb, nframes - brkb);
199  removed = true;
200  }
201  }
202  else
203  {
204  /* Extend break "bb" to cover "bbnext"; delete "bbnext". */
205  if (verbose)
206  {
207  long long old1 = brkb;
208  long long old2 = segb - 1;
209  long long new1 = brkb;
210  long long new2 = bbnext.key() + *bbnext - 1;
211  LOG(VB_COMMFLAG, LOG_INFO,
212  QString("Removing segment %1-%2 (%3-%4)")
213  .arg(frameToTimestamp(segb + 1, fps))
214  .arg(frameToTimestamp(sege + 1, fps))
215  .arg(segb + 1).arg(sege + 1));
216  LOG(VB_COMMFLAG, LOG_INFO,
217  QString("Replacing break %1-%2 (%3-%4)"
218  " with %5-%6 (%7-%8)")
219  .arg(frameToTimestamp(old1 + 1, fps))
220  .arg(frameToTimestamp(old2 + 1, fps))
221  .arg(old1 + 1).arg(old2 + 1)
222  .arg(frameToTimestamp(new1 + 1, fps))
223  .arg(frameToTimestamp(new2 + 1, fps))
224  .arg(new1 + 1).arg(new2 + 1));
225  }
226  breakMap->remove(brkb);
227  breakMap->insert(brkb, bbnext.key() + *bbnext - brkb);
228 
229  bb = bbnext;
230  ++bbnext;
231  if (verbose)
232  {
233  long long start = bb.key();
234  long long end = start + *bb - 1;
235  LOG(VB_COMMFLAG, LOG_INFO,
236  QString("Removing break %1-%2 (%3-%4)")
237  .arg(frameToTimestamp(start + 1, fps))
238  .arg(frameToTimestamp(end + 1, fps))
239  .arg(start + 1).arg(end + 1));
240  }
241  breakMap->erase(bb);
242 
243  removed = true;
244  }
245  }
246 
247  return removed;
248 }
249 
250 FrameAnalyzer::FrameMap::const_iterator
252  long long markend)
253 {
254  /*
255  * Search forwards to find the earliest block "block" such that
256  *
257  * mark <= blockbegin < markend
258  *
259  * Return frameMap->constEnd() if there is no such block.
260  */
261  FrameAnalyzer::FrameMap::const_iterator block = frameMap->constBegin();
262 
263  for (; block != frameMap->constEnd(); ++block)
264  {
265  const long long bb = block.key();
266  const long long ee = bb + *block;
267  if (mark < ee)
268  {
269  if (mark <= bb && bb < markend)
270  return block;
271  break;
272  }
273  }
274  return frameMap->constEnd();
275 }
276 
277 FrameAnalyzer::FrameMap::const_iterator
279  long long markbegin, long long mark)
280 {
281  /*
282  * Search backards to find the latest block "block" such that
283  *
284  * markbegin < blockend <= mark
285  *
286  * Return frameMap->constEnd() if there is no such block.
287  */
288  FrameAnalyzer::FrameMap::const_iterator block = frameMap->constEnd();
289  for (--block; block != frameMap->constBegin(); --block)
290  {
291  const long long bb = block.key();
292  const long long ee = bb + *block;
293  if (bb < mark)
294  {
295  if (markbegin < ee && ee <= mark)
296  return block;
297  break;
298  }
299  }
300  return frameMap->constEnd();
301 }
302 
303 }; /* namespace */
304 
305 /* vim: set expandtab tabstop=4 shiftwidth=4: */
frameAnalyzer::rrccinrect
bool rrccinrect(int rr, int cc, int rrow, int rcol, int rwidth, int rheight)
Definition: FrameAnalyzer.cpp:10
frameAnalyzer::removeShortBreaks
bool removeShortBreaks(FrameAnalyzer::FrameMap *breakMap, float fps, int minbreaklen, bool verbose)
Definition: FrameAnalyzer.cpp:94
CommDetector2.h
cc
Definition: cc.h:10
FrameAnalyzer::FrameMap
QMap< long long, long long > FrameMap
Definition: FrameAnalyzer.h:45
arg
arg(title).arg(filename).arg(doDelete))
LOG
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
Definition: mythlogging.h:23
frameAnalyzer::removeShortSegments
bool removeShortSegments(FrameAnalyzer::FrameMap *breakMap, long long nframes, float fps, int minseglen, bool verbose)
Definition: FrameAnalyzer.cpp:141
frameAnalyzer::frameMapSearchBackwards
FrameAnalyzer::FrameMap::const_iterator frameMapSearchBackwards(const FrameAnalyzer::FrameMap *frameMap, long long markbegin, long long mark)
Definition: FrameAnalyzer.cpp:278
mythlogging.h
mark
Definition: lang.cpp:21
FrameAnalyzer.h
frameAnalyzer::frameAnalyzerMapSum
long long frameAnalyzerMapSum(const FrameAnalyzer::FrameMap *frameMap)
Definition: FrameAnalyzer.cpp:87
frameAnalyzer::frameAnalyzerReportMap
void frameAnalyzerReportMap(const FrameAnalyzer::FrameMap *frameMap, float fps, const char *comment)
Definition: FrameAnalyzer.cpp:17
frameAnalyzer::frameMapSearchForwards
FrameAnalyzer::FrameMap::const_iterator frameMapSearchForwards(const FrameAnalyzer::FrameMap *frameMap, long long mark, long long markend)
Definition: FrameAnalyzer.cpp:251
commDetector2
Definition: CommDetector2.cpp:194
hardwareprofile.distros.mythtv_data.makeopts.verbose
verbose
Definition: makeopts.py:60
frameAnalyzer
Definition: FrameAnalyzer.cpp:7
commDetector2::frameToTimestampms
QString frameToTimestampms(long long frameno, float fps)
Definition: CommDetector2.cpp:262
commDetector2::frameToTimestamp
QString frameToTimestamp(long long frameno, float fps)
Definition: CommDetector2.cpp:254
frameAnalyzer::frameAnalyzerReportMapms
void frameAnalyzerReportMapms(const FrameAnalyzer::FrameMap *frameMap, float fps, const char *comment)
Definition: FrameAnalyzer.cpp:52