static ImBuf *movieclip_load_movie_file(MovieClip *clip, MovieClipUser *user, int framenr, int flag) { ImBuf *ibuf = NULL; int tc = get_timecode(clip, flag); int proxy = rendersize_to_proxy(user, flag); movieclip_open_anim_file(clip); if (clip->anim) { int dur; int fra; dur = IMB_anim_get_duration(clip->anim, tc); fra = framenr - 1; if (fra < 0) fra = 0; if (fra > (dur - 1)) fra = dur - 1; ibuf = IMB_anim_absolute(clip->anim, fra, tc, proxy); } return ibuf; }
static void put_postprocessed_frame_to_cache(MovieClip *clip, MovieClipUser *user, ImBuf *ibuf, int flag, int postprocess_flag) { MovieClipCache *cache = clip->cache; MovieTrackingCamera *camera = &clip->tracking.camera; cache->postprocessed.framenr = user->framenr; cache->postprocessed.flag = postprocess_flag; if (flag & MCLIP_USE_PROXY) { cache->postprocessed.proxy = rendersize_to_proxy(user, flag); cache->postprocessed.render_flag = user->render_flag; } else { cache->postprocessed.proxy = IMB_PROXY_NONE; cache->postprocessed.render_flag = 0; } if (need_undistortion_postprocess(user)) { copy_v2_v2(cache->postprocessed.principal, camera->principal); copy_v3_v3(&cache->postprocessed.k1, &camera->k1); cache->postprocessed.undistortion_used = TRUE; } else { cache->postprocessed.undistortion_used = FALSE; } IMB_refImBuf(ibuf); if (cache->postprocessed.ibuf) IMB_freeImBuf(cache->postprocessed.ibuf); cache->postprocessed.ibuf = ibuf; }
static ImBuf *put_postprocessed_frame_to_cache(MovieClip *clip, MovieClipUser *user, ImBuf *ibuf, int flag, int postprocess_flag) { MovieClipCache *cache = clip->cache; MovieTrackingCamera *camera = &clip->tracking.camera; ImBuf *postproc_ibuf = NULL; if (cache->postprocessed.ibuf) IMB_freeImBuf(cache->postprocessed.ibuf); cache->postprocessed.framenr = user->framenr; cache->postprocessed.flag = postprocess_flag; if (flag & MCLIP_USE_PROXY) { cache->postprocessed.proxy = rendersize_to_proxy(user, flag); cache->postprocessed.render_flag = user->render_flag; } else { cache->postprocessed.proxy = IMB_PROXY_NONE; cache->postprocessed.render_flag = 0; } if (need_undistortion_postprocess(user, flag)) { copy_v2_v2(cache->postprocessed.principal, camera->principal); copy_v3_v3(&cache->postprocessed.k1, &camera->k1); cache->postprocessed.undistoriton_used = TRUE; postproc_ibuf = get_undistorted_ibuf(clip, NULL, ibuf); } else { cache->postprocessed.undistoriton_used = FALSE; } if (postprocess_flag) { int disable_red = postprocess_flag & MOVIECLIP_DISABLE_RED, disable_green = postprocess_flag & MOVIECLIP_DISABLE_GREEN, disable_blue = postprocess_flag & MOVIECLIP_DISABLE_BLUE, grayscale = postprocess_flag & MOVIECLIP_PREVIEW_GRAYSCALE; if (!postproc_ibuf) postproc_ibuf = IMB_dupImBuf(ibuf); if (disable_red || disable_green || disable_blue || grayscale) BKE_tracking_disable_imbuf_channels(postproc_ibuf, disable_red, disable_green, disable_blue, 1); } IMB_refImBuf(postproc_ibuf); cache->postprocessed.ibuf = postproc_ibuf; if (cache->stabilized.ibuf) { /* force stable buffer be re-calculated */ IMB_freeImBuf(cache->stabilized.ibuf); cache->stabilized.ibuf = NULL; } return postproc_ibuf; }
/* get segments of cached frames. useful for debugging cache policies */ void BKE_movieclip_get_cache_segments(MovieClip *clip, MovieClipUser *user, int *totseg_r, int **points_r) { *totseg_r = 0; *points_r = NULL; if (clip->cache) { int proxy = rendersize_to_proxy(user, clip->flag); IMB_moviecache_get_cache_segments(clip->cache->moviecache, proxy, user->render_flag, totseg_r, points_r); } }
static ImBuf *get_stable_cached_frame(MovieClip *clip, MovieClipUser *user, ImBuf *reference_ibuf, int framenr, int postprocess_flag) { MovieClipCache *cache = clip->cache; MovieTracking *tracking = &clip->tracking; ImBuf *stableibuf; float tloc[2], tscale, tangle; short proxy = IMB_PROXY_NONE; int render_flag = 0; int clip_framenr = BKE_movieclip_remap_scene_to_clip_frame(clip, framenr); if (clip->flag & MCLIP_USE_PROXY) { proxy = rendersize_to_proxy(user, clip->flag); render_flag = user->render_flag; } /* there's no cached frame or it was calculated for another frame */ if (!cache->stabilized.ibuf || cache->stabilized.framenr != framenr) return NULL; if (cache->stabilized.reference_ibuf != reference_ibuf) return NULL; /* cached ibuf used different proxy settings */ if (cache->stabilized.render_flag != render_flag || cache->stabilized.proxy != proxy) return NULL; if (cache->stabilized.postprocess_flag != postprocess_flag) return NULL; /* stabilization also depends on pixel aspect ratio */ if (cache->stabilized.aspect != tracking->camera.pixel_aspect) return NULL; if (cache->stabilized.filter != tracking->stabilization.filter) return NULL; stableibuf = cache->stabilized.ibuf; BKE_tracking_stabilization_data_get(&clip->tracking, clip_framenr, stableibuf->x, stableibuf->y, tloc, &tscale, &tangle); /* check for stabilization parameters */ if (tscale != cache->stabilized.scale || tangle != cache->stabilized.angle || !equals_v2v2(tloc, cache->stabilized.loc)) { return NULL; } IMB_refImBuf(stableibuf); return stableibuf; }
static ImBuf *movieclip_load_movie_file(MovieClip *clip, MovieClipUser *user, int framenr, int flag) { ImBuf *ibuf = NULL; int tc = get_timecode(clip, flag); int proxy = rendersize_to_proxy(user, flag); movieclip_open_anim_file(clip); if (clip->anim) { int fra = framenr - clip->start_frame + clip->frame_offset; ibuf = IMB_anim_absolute(clip->anim, fra, tc, proxy); } return ibuf; }
static bool put_imbuf_cache(MovieClip *clip, MovieClipUser *user, ImBuf *ibuf, int flag, bool destructive) { MovieClipImBufCacheKey key; if (!clip->cache) { struct MovieCache *moviecache; // char cache_name[64]; // BLI_snprintf(cache_name, sizeof(cache_name), "movie %s", clip->id.name); clip->cache = MEM_callocN(sizeof(MovieClipCache), "movieClipCache"); moviecache = IMB_moviecache_create("movieclip", sizeof(MovieClipImBufCacheKey), moviecache_hashhash, moviecache_hashcmp); IMB_moviecache_set_getdata_callback(moviecache, moviecache_keydata); IMB_moviecache_set_priority_callback(moviecache, moviecache_getprioritydata, moviecache_getitempriority, moviecache_prioritydeleter); clip->cache->moviecache = moviecache; clip->cache->sequence_offset = -1; } key.framenr = user_frame_to_cache_frame(clip, user->framenr); if (flag & MCLIP_USE_PROXY) { key.proxy = rendersize_to_proxy(user, flag); key.render_flag = user->render_flag; } else { key.proxy = IMB_PROXY_NONE; key.render_flag = 0; } if (destructive) { IMB_moviecache_put(clip->cache->moviecache, &key, ibuf); return true; } else { return IMB_moviecache_put_if_possible(clip->cache->moviecache, &key, ibuf); } }
static bool has_imbuf_cache(MovieClip *clip, MovieClipUser *user, int flag) { if (clip->cache) { MovieClipImBufCacheKey key; key.framenr = user_frame_to_cache_frame(clip, user->framenr); if (flag & MCLIP_USE_PROXY) { key.proxy = rendersize_to_proxy(user, flag); key.render_flag = user->render_flag; } else { key.proxy = IMB_PROXY_NONE; key.render_flag = 0; } return IMB_moviecache_has_frame(clip->cache->moviecache, &key); } return false; }
static ImBuf *put_stabilized_frame_to_cache(MovieClip *clip, MovieClipUser *user, ImBuf *ibuf, int framenr, int postprocess_flag) { MovieClipCache *cache = clip->cache; MovieTracking *tracking = &clip->tracking; ImBuf *stableibuf; float tloc[2], tscale, tangle; int clip_framenr = BKE_movieclip_remap_scene_to_clip_frame(clip, framenr); stableibuf = BKE_tracking_stabilize_frame(&clip->tracking, clip_framenr, ibuf, tloc, &tscale, &tangle); copy_v2_v2(cache->stabilized.loc, tloc); cache->stabilized.reference_ibuf = ibuf; cache->stabilized.scale = tscale; cache->stabilized.angle = tangle; cache->stabilized.framenr = framenr; cache->stabilized.aspect = tracking->camera.pixel_aspect; cache->stabilized.filter = tracking->stabilization.filter; if (clip->flag & MCLIP_USE_PROXY) { cache->stabilized.proxy = rendersize_to_proxy(user, clip->flag); cache->stabilized.render_flag = user->render_flag; } else { cache->stabilized.proxy = IMB_PROXY_NONE; cache->stabilized.render_flag = 0; } cache->stabilized.postprocess_flag = postprocess_flag; if (cache->stabilized.ibuf) IMB_freeImBuf(cache->stabilized.ibuf); cache->stabilized.ibuf = stableibuf; IMB_refImBuf(stableibuf); return stableibuf; }
static ImBuf *get_postprocessed_cached_frame(MovieClip *clip, MovieClipUser *user, int flag, int postprocess_flag) { MovieClipCache *cache = clip->cache; int framenr = user->framenr; short proxy = IMB_PROXY_NONE; int render_flag = 0; if (flag & MCLIP_USE_PROXY) { proxy = rendersize_to_proxy(user, flag); render_flag = user->render_flag; } /* no cache or no cached postprocessed image */ if (!clip->cache || !clip->cache->postprocessed.ibuf) return NULL; /* postprocessing happened for other frame */ if (cache->postprocessed.framenr != framenr) return NULL; /* cached ibuf used different proxy settings */ if (cache->postprocessed.render_flag != render_flag || cache->postprocessed.proxy != proxy) return NULL; if (cache->postprocessed.flag != postprocess_flag) return NULL; if (need_undistortion_postprocess(user)) { if (!check_undistortion_cache_flags(clip)) return NULL; } else if (cache->postprocessed.undistortion_used) return NULL; IMB_refImBuf(cache->postprocessed.ibuf); return cache->postprocessed.ibuf; }
static void put_imbuf_cache(MovieClip *clip, MovieClipUser *user, ImBuf *ibuf, int flag) { MovieClipImBufCacheKey key; if (!clip->cache) { clip->cache = MEM_callocN(sizeof(MovieClipCache), "movieClipCache"); clip->cache->moviecache = IMB_moviecache_create(sizeof(MovieClipImBufCacheKey), moviecache_hashhash, moviecache_hashcmp, moviecache_keydata); } key.framenr = user->framenr; if (flag & MCLIP_USE_PROXY) { key.proxy = rendersize_to_proxy(user, flag); key.render_flag = user->render_flag; } else { key.proxy = IMB_PROXY_NONE; key.render_flag = 0; } IMB_moviecache_put(clip->cache->moviecache, &key, ibuf); }