Skip to main content
Version: 7.0

Video modifier

The video modifier feature allows you to modify local video frames before they are transmitted. This feature enables your application to apply real-time effects, filters, or transformations to the outgoing video stream.

Supported call typeMinimum SDK version
1-to-1 call, group call (conference)PlanetKit 7.0
Note
  • The video modifier only applies to local video captured from the camera.
  • Video modification processing should be designed to minimize computational cost and latency in order to prevent frame drops and quality degradation.

Use cases

The main use cases for video modifiers are as follows.

  • Real-time video effects and filters
  • Beauty filters and facial enhancements
  • Color correction and adjustments

Implementation steps

To implement the video modifier feature, follow these steps.

Implement a video modifier

Create a class that inherits from IVideoInterceptor to modify video frames.

#include "PlanetKit.h"
#include "IPlanetKitVideoInterceptor.h"

class VideoModifier : public PlanetKit::IVideoInterceptor {
public:
PlanetKit::SVideoFrame* ProcessVideoFrame(PlanetKit::SVideoFrame* pVideoFrame) override {
if (!pVideoFrame) {
return nullptr;
}

// Access video frame properties from SVideoFrame structure:
// - pVideoFrame->pbuffer: Pointer to the frame buffer
// - pVideoFrame->unBufferSize: Allocated buffer size
// - pVideoFrame->unDataLength: Actual length (in bytes) of buffer data
// - pVideoFrame->unWidth: Frame width in pixels
// - pVideoFrame->unHeight: Frame height in pixels
// - pVideoFrame->llTick: Tick count in microseconds
// - pVideoFrame->llTimeStamp: Timestamp
// - pVideoFrame->llDuration: Frame duration
// - pVideoFrame->eRotation: Rotation angle
// - pVideoFrame->bSubgroupMain: Whether frame belongs to main room
// - pVideoFrame->szSubgroupName: Subgroup name (if bSubgroupMain is false)

// Process the frame and apply your effects
// You can either:
// 1. Process synchronously: Modify the frame and return the pointer
// 2. Process asynchronously: Return nullptr and call delegate->onProcessFinished later

// Example: Apply your custom effect synchronously
ApplyVideoEffect(pVideoFrame);

// Return the modified frame pointer for synchronous processing
// Return nullptr if processing asynchronously (must register a delegate)
return pVideoFrame;
}

bool RegisterDelegate(PlanetKit::IVideoInterceptorDelegate* pDelegate) override {
m_pDelegate = pDelegate;
return true;
}

bool DeregisterDelegate() override {
m_pDelegate = nullptr;
return true;
}

private:
void ApplyVideoEffect(PlanetKit::SVideoFrame* pVideoFrame) {
// Implement your video effect logic here
// Note: This runs on the camera capture thread, keep processing lightweight
}

PlanetKit::IVideoInterceptorDelegate* m_pDelegate = nullptr;
};

Set the video modifier

Register the modifier with the camera controller to start modifying video frames.

// Get camera controller instance
PlanetKit::CameraControllerPtr pCameraController = PlanetKit::PlanetKitManager::GetInstance()->GetCameraController();

// Create and register the modifier
PlanetKit::IVideoInterceptorPtr pVideoModifier = PlanetKit::MakeAutoPtr<VideoModifier>();

bool success = pCameraController->RegisterVideoInterceptor(pVideoModifier);
if (!success) {
// Handle error
}

Clear the video modifier

Unregister the modifier to stop modifying video frames.

PlanetKit::CameraControllerPtr pCameraController = PlanetKit::PlanetKitManager::GetInstance()->GetCameraController();

// Deregister the modifier
bool success = pCameraController->DeregisterVideoInterceptor();
if (!success) {
// Handle error
}

The APIs related to the video modifier feature are as follows.