Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow sources to know when it is being previewed #11898

Open
wants to merge 5 commits into
base: master
Choose a base branch
from

Conversation

BitRate27
Copy link

@BitRate27 BitRate27 commented Feb 25, 2025

Description

A preview state is added to the OBS API to allow sources to determine if they are in the current preview scene or not. The new preview state APIs work similiar to the existing activate/deactivate/show/hide APIs where a callback is optionally provided to notify the source of changes in state. Building on this new preview state, toggling of visibility of a source in the preview scene will change the preview state and notify the source immediately.

The changes consist of three parts:

  • Inc/dec new preview_refs counts and inc/dec activate_refs counts correctly
  • C APIs for exposing preview state
  • Lua APIs for exposing preview state

This PR contains 5 commits:

obs-source: Add preview and depreview states to sources
    libobs/obs-source.c
    libobs/obs-internal.h
libobs: Add preview and depreview APIs 
    libobs/obs.h
    libobs/obs-source.h
obs-scene: Fix ref count bugs* 
    libobs/obs-scene.c
obs-scripting: Add preview and depreview callbacks to lua API
    shared/obs-scripting/obs-scripting-lua-source.c
frontend: Set preview state on scene changes
    frontend/widgets/OBSBasic_StudioMode.cpp
    frontend/widgets/OBSBasic_Transitions.cpp
  • It should be noted that there were two problems with how active_ref counts were handled at the scene level. The first issue was that the active_refs was getting decreased while applying audio actions. The problem is they were never increased to begin with, or at least not in the current code base, so the active_refs count would go negative. The second issue is that repeatedly toggling the item visibility would increase the active_refs count as it was only being increased when turning on visibility. The fix was to decrease active_refs when visibility is turned off.

The big part of this PR is seperating the show_refs count from the activate_refs. To do this a new SHOW_VIEW enum was added to the AUX_VIEW and MAIN_VIEW enums. This allows callers (specifically projectors or multiview) to only inc/dec show_refs and not change activate or preview ref counts.

Motivation and Context

Currently a source can know when it is being shown and when it is active on the main "program" scene. In the case of studio mode, a source may be also be shown in the current preview scene. When a source is in the current program scene, it is considered 'shown' and 'active' by OBS. If it is only in preview scene, it is just 'shown'. Also, when a source is shown as part of a scene in Multiview or on a projector, the source will also have a state of 'shown'. This causes a problem when a source needs to implement a tally. A tally is traditionally a red (active) or green (preview) light on the camera to give the camera operator or video subject indication as to if the camera is live/on program (red) or being previewed (green), or not being used (no light). This means the condition: shown AND not active is not indicative of being in the current preview scene.

So the basic issue is that show state is used for projection/multiview and when a source is in the current program scene. This PR fixes this problem by introducing a preview state.

This issue has been documented by a DistroAV (formerly obs-ndi) user, complaining that his tally light on his NDI camera flashes red/green/red/green/... when it is in the current program scene and not in preview. DistroAV/DistroAV#687

The issue can also be witnessed in NDI Studio Monitor when viewing the source when it is in the current program scene in OBS, but not in the current preview scene. A red and a green bar appears at the top of the video. Also, a green bar appears when the NDI source is being projected or in multiview, and not in the current preview scene.

There is also a OBS API feature request for this here:
https://ideas.obsproject.com/posts/1271/add-obs_source_inpreview-to-sdk

Finally a long time problem of the Multi-view causing all NDI sources to show as in
preview, is here: DistroAV/DistroAV#318

Type of change

  • New feature (non-breaking change which adds functionality)

API considerations

Since the show/hide API is used by sources to know if OBS is using the source in any way, we cannot change the meaning of show/hide, without breaking the API. With this change, new APIs were added so the source can simply and accurately determine if a source is being previewed and immediately react to changes the user makes to the source state.

Exactly mirroring the activate/deactivate APIs, this PR adds the following APIs:

bool obs_source_preview(const obs_source_t *source);
void obs_source_inc_preview(obs_source_t *source);
void obs_source_dec_preview(obs_source_t *source);

struct obs_source_info {...
	void (*preview)(void *data);
	void (*depreview)(void *data);
}

Testing

To test, I modified DistroAV to use the new preview APIs. I then created 3 Test Pattern sources in NDI Tools. I then opened Studio Monitor on each Test Pattern Source, and turned on Tally display. I created a collection of 3 scenes as shown in the table below, along with results of the testing.

Screenshot 2025-02-23 173234

The table shows the tally after each step for each source. Sometimes the tally is red and green.

To aid in testing by reviewers of this PR, I created a Lua script that creates an OBS source called "Tally Test". The script will log when any of the 6 callbacks are called: activate, deactivate, preview, depreview, show and hide. Pleae find the Lua script here:

testtally.txt

Finally, the tests were done in Normal (non Studio) mode with no Preview scene and all callbacks were called correctly.

Checklist:

  • My code has been run through clang-format.
  • I have read the contributing document.
  • My code is not on the master branch.
  • The code has been tested.
  • All commit messages are properly formatted and commits squashed where appropriate.
  • I have included updates to all appropriate documentation.

@WizardCM WizardCM added the New Feature New feature or plugin label Feb 26, 2025
@WizardCM
Copy link
Member

WizardCM commented Mar 2, 2025

While I do agree there'd be some benefit to a source knowing when it's only in preview, I feel the provided examples are irrelevant to the OBS implementation-side.

For the first, the tally light flickering between two states should simply prioritise one over the other.

For the second, the behaviour in NDI Studio Monitor sounds intentional, but if it's not, you should report it to NDI.

@BitRate27
Copy link
Author

While I do agree there'd be some benefit to a source knowing when it's only in preview, I feel the provided examples are irrelevant to the OBS implementation-side.

For the first, the tally light flickering between two states should simply prioritise one over the other.

For the second, the behaviour in NDI Studio Monitor sounds intentional, but if it's not, you should report it to NDI.

The examples were included because they were the motivation for adding the API. The problem is not how the camera or Studio Monitor is showing tallies when a camera is in both preview and program. There is no way to fully support preview tally in a source plugin in OBS, this is why this new API is needed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
New Feature New feature or plugin
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants