Stefan Schuermans commited on 2016-12-18 13:18:36
Showing 1 changed files, with 130 additions and 0 deletions.
... | ... |
@@ -214,6 +214,114 @@ static void copy_rect(stBlinkenMovie *pMovie, char *str_file, |
214 | 214 |
} |
215 | 215 |
} |
216 | 216 |
|
217 |
+static stBlinkenMovie * scroll(stBlinkenMovie *pMovie, |
|
218 |
+ const char * str_direction, |
|
219 |
+ const char * str_width_height, |
|
220 |
+ const char * str_duration) |
|
221 |
+{ |
|
222 |
+ enum { |
|
223 |
+ DirNone, DirLeft, DirRight, DirUp, DirDown, |
|
224 |
+ } dir = DirNone; |
|
225 |
+ int width_height, duration, height, width, channels, maxval, |
|
226 |
+ new_height, new_width, sy, sx, dy, dx, steps, step; |
|
227 |
+ stBlinkenFrame *pScroll, *pFrame; |
|
228 |
+ |
|
229 |
+ // direction |
|
230 |
+ if (strcmp(str_direction, "left") == 0) |
|
231 |
+ dir = DirLeft; |
|
232 |
+ else if (strcmp(str_direction, "right") == 0) |
|
233 |
+ dir = DirRight; |
|
234 |
+ else if (strcmp(str_direction, "up") == 0) |
|
235 |
+ dir = DirUp; |
|
236 |
+ else if (strcmp(str_direction, "down") == 0) |
|
237 |
+ dir = DirDown; |
|
238 |
+ |
|
239 |
+ // check |
|
240 |
+ if (dir == DirNone) { |
|
241 |
+ printf("invalid direction \"%s\" for \"-S\" (left, right, up, down)\n", |
|
242 |
+ str_direction); |
|
243 |
+ return pMovie; |
|
244 |
+ } |
|
245 |
+ if (sscanf(str_width_height, "%u", &width_height) != 1 || width_height < 1) { |
|
246 |
+ printf("invalid width/height \"%s\" for \"-S\"\n", str_width_height); |
|
247 |
+ return pMovie; |
|
248 |
+ } |
|
249 |
+ if (sscanf(str_duration, "%u", &duration) != 1 || duration < 1) { |
|
250 |
+ printf("invalid duration \"%s\" for \"-S\"\n", str_duration); |
|
251 |
+ return pMovie; |
|
252 |
+ } |
|
253 |
+ if (BlinkenMovieGetFrameCnt(pMovie) < 1) { |
|
254 |
+ printf("empty movie not allowed for \"-S\"\n"); |
|
255 |
+ return pMovie; |
|
256 |
+ } |
|
257 |
+ |
|
258 |
+ // get number of steps |
|
259 |
+ height = BlinkenMovieGetHeight(pMovie); |
|
260 |
+ width = BlinkenMovieGetWidth(pMovie); |
|
261 |
+ channels = BlinkenMovieGetChannels(pMovie); |
|
262 |
+ maxval = BlinkenMovieGetMaxval(pMovie); |
|
263 |
+ new_height = height; |
|
264 |
+ new_width = width; |
|
265 |
+ sy = 0; |
|
266 |
+ sx = 0; |
|
267 |
+ dy = 1; |
|
268 |
+ dx = 1; |
|
269 |
+ switch (dir) { |
|
270 |
+ case DirNone: |
|
271 |
+ return pMovie; |
|
272 |
+ case DirRight: |
|
273 |
+ sx = 1; // prepare for sx *= steps |
|
274 |
+ dx = -1; |
|
275 |
+ // fall through |
|
276 |
+ case DirLeft: |
|
277 |
+ dy = 0; |
|
278 |
+ steps = width - width_height + 1; |
|
279 |
+ sx *= (steps - 1); // before this line, sx was 0 or 1 |
|
280 |
+ if (steps < 1) { |
|
281 |
+ printf("invalid width %u for \"-S left/right\" on movie of width %u\n", |
|
282 |
+ width_height, width); |
|
283 |
+ return pMovie; |
|
284 |
+ } |
|
285 |
+ new_width = width_height; |
|
286 |
+ break; |
|
287 |
+ case DirDown: |
|
288 |
+ sy = 1; // prepare for sy *= steps |
|
289 |
+ dy = -1; |
|
290 |
+ // fall through |
|
291 |
+ case DirUp: |
|
292 |
+ dx = 0; |
|
293 |
+ steps = height - width_height + 1; |
|
294 |
+ sy *= (steps - 1); // before this line, sy was 0 or 1 |
|
295 |
+ if (steps < 1) { |
|
296 |
+ printf("invalid height %u for \"-S up/down\" on movie of height %u\n", |
|
297 |
+ width_height, width); |
|
298 |
+ return pMovie; |
|
299 |
+ } |
|
300 |
+ new_height = width_height; |
|
301 |
+ break; |
|
302 |
+ } |
|
303 |
+ |
|
304 |
+ // get copy of first frame |
|
305 |
+ pScroll = BlinkenFrameClone(BlinkenMovieGetFrame(pMovie, 1)); |
|
306 |
+ BlinkenFrameSetDuration(pScroll, duration); |
|
307 |
+ |
|
308 |
+ // free old movie |
|
309 |
+ BlinkenMovieFree(pMovie); |
|
310 |
+ |
|
311 |
+ // create new movie scrolling the frame |
|
312 |
+ pMovie = BlinkenMovieNew(new_height, new_width, channels, maxval); |
|
313 |
+ for (step = 0; step < steps; ++step, sy += dy, sx += dx) { |
|
314 |
+ pFrame = BlinkenFrameClone(pScroll); |
|
315 |
+ BlinkenFrameCrop(pFrame, sy, sx, new_height, new_width); |
|
316 |
+ BlinkenMovieAppendFrame(pMovie, pFrame); |
|
317 |
+ } |
|
318 |
+ |
|
319 |
+ // free scrolled frame |
|
320 |
+ BlinkenFrameFree(pScroll); |
|
321 |
+ |
|
322 |
+ return pMovie; |
|
323 |
+} |
|
324 |
+ |
|
217 | 325 |
int main(int argCnt, char **args) |
218 | 326 |
{ |
219 | 327 |
stBlinkenMovie *pMovie; |
... | ... |
@@ -273,6 +381,8 @@ int main(int argCnt, char **args) |
273 | 381 |
" generate a test movie and append it to current video\n" |
274 | 382 |
" -C <file> <src-x>,<src-y> <width>x<height> <dest-x>,<dest-y>\n" |
275 | 383 |
" copy rectangular section of other movie\n" |
384 |
+ " -S {left|right|up|down} <width/height> <duration>\n" |
|
385 |
+ " scroll first frame of current movie (duration in ms)\n" |
|
276 | 386 |
" -Rcw\n" |
277 | 387 |
" rotate movie 90 degrees clockwise\n" |
278 | 388 |
" -Rccw\n" |
... | ... |
@@ -639,6 +749,26 @@ int main(int argCnt, char **args) |
639 | 749 |
} else |
640 | 750 |
printf("missing file name of source movie for \"-C\"\n"); |
641 | 751 |
} |
752 |
+ // scroll first frame of current movie |
|
753 |
+ else if (strcmp(args[i], "-S") == 0) { |
|
754 |
+ if (i + 3 < argCnt) { |
|
755 |
+ const char *str_direction, *str_width_height, *str_duration; |
|
756 |
+ i++; |
|
757 |
+ str_direction = args[i]; |
|
758 |
+ i++; |
|
759 |
+ str_width_height = args[i]; |
|
760 |
+ i++; |
|
761 |
+ str_duration = args[i]; |
|
762 |
+ pMovie = scroll(pMovie, str_direction, str_width_height, str_duration); |
|
763 |
+ } else if (i + 2 < argCnt) { |
|
764 |
+ printf("missing duration for \"-S\"\n"); |
|
765 |
+ i += 2; |
|
766 |
+ } else if (i + 1 < argCnt) { |
|
767 |
+ printf("missing width/height for \"-S\"\n"); |
|
768 |
+ i++; |
|
769 |
+ } else |
|
770 |
+ printf("missing direction (left, right, up, down) for \"-S\"\n"); |
|
771 |
+ } |
|
642 | 772 |
// rotate movie 90 degrees clockwise |
643 | 773 |
else if (strcmp(args[i], "-Rcw") == 0) { |
644 | 774 |
if (pMovie == NULL) |
645 | 775 |