0
0
mirror of https://github.com/obsproject/obs-studio.git synced 2024-09-20 04:42:18 +02:00

libobs: Ensure async source sizes are always reset

If an async source is cropped on one side, then when the program is
restarted and the source is loaded from file, the async source will
start out with a width/height of zero.  This will cause the async source
to not be drawn if cropping or scale filtering is added to the scene
item, because it has to be rendered to a texture first.  However, the
source cannot reset its size until it's drawn, so it leaves it in
perpetual state of having a 0x0 size.

This fixes that problem by ensuring that the async source size is always
reset even when not being rendered.

Close jp9000/obs-studio#686
This commit is contained in:
Jim 2016-11-05 18:34:02 +08:00 committed by jp9000
parent 3b616823a1
commit 9982581a4f
2 changed files with 38 additions and 22 deletions

View File

@ -593,6 +593,7 @@ struct obs_source {
int async_plane_offset[2];
bool async_flip;
bool async_active;
bool async_update_texture;
DARRAY(struct async_frame) async_cache;
DARRAY(struct obs_source_frame*)async_frames;
pthread_mutex_t async_mutex;

View File

@ -921,6 +921,35 @@ void obs_source_deactivate(obs_source_t *source, enum view_type type)
static inline struct obs_source_frame *get_closest_frame(obs_source_t *source,
uint64_t sys_time);
bool set_async_texture_size(struct obs_source *source,
const struct obs_source_frame *frame);
static void async_tick(obs_source_t *source)
{
uint64_t sys_time = obs->video.video_time;
pthread_mutex_lock(&source->async_mutex);
if (deinterlacing_enabled(source)) {
deinterlace_process_last_frame(source, sys_time);
} else {
if (source->cur_async_frame) {
remove_async_frame(source,
source->cur_async_frame);
source->cur_async_frame = NULL;
}
source->cur_async_frame = get_closest_frame(source,
sys_time);
}
source->last_sys_timestamp = sys_time;
pthread_mutex_unlock(&source->async_mutex);
if (source->cur_async_frame)
source->async_update_texture = set_async_texture_size(source,
source->cur_async_frame);
}
void obs_source_video_tick(obs_source_t *source, float seconds)
{
@ -932,27 +961,8 @@ void obs_source_video_tick(obs_source_t *source, float seconds)
if (source->info.type == OBS_SOURCE_TYPE_TRANSITION)
obs_transition_tick(source);
if ((source->info.output_flags & OBS_SOURCE_ASYNC) != 0) {
uint64_t sys_time = obs->video.video_time;
pthread_mutex_lock(&source->async_mutex);
if (deinterlacing_enabled(source)) {
deinterlace_process_last_frame(source, sys_time);
} else {
if (source->cur_async_frame) {
remove_async_frame(source,
source->cur_async_frame);
source->cur_async_frame = NULL;
}
source->cur_async_frame = get_closest_frame(source,
sys_time);
}
source->last_sys_timestamp = sys_time;
pthread_mutex_unlock(&source->async_mutex);
}
if ((source->info.output_flags & OBS_SOURCE_ASYNC) != 0)
async_tick(source);
if (source->defer_update)
obs_source_deferred_update(source);
@ -1333,6 +1343,8 @@ bool set_async_texture_size(struct obs_source *source,
source->async_height = frame->height;
source->async_format = frame->format;
gs_enter_context(obs->video.graphics);
gs_texture_destroy(source->async_texture);
gs_texture_destroy(source->async_prev_texture);
gs_texrender_destroy(source->async_texrender);
@ -1367,6 +1379,8 @@ bool set_async_texture_size(struct obs_source *source,
if (deinterlacing_enabled(source))
set_deinterlace_texture_size(source);
gs_leave_context();
return !!source->async_texture;
}
@ -1614,10 +1628,11 @@ static void obs_source_update_async_video(obs_source_t *source)
os_gettime_ns() - frame->timestamp;
source->timing_set = true;
if (set_async_texture_size(source, frame)) {
if (source->async_update_texture) {
update_async_texture(source, frame,
source->async_texture,
source->async_texrender);
source->async_update_texture = false;
}
obs_source_release_frame(source, frame);