KlvInjectorEncodeDemoApp

KlvInjectorEncodeDemoApp is an example that demonstrates how to create a video from uncompressed frames (bitmaps), add Klv metadata and create STANAG 4609 compliant stream or file.

Command line arguments

Demo application will accept the following arguments

Short Command Description
-o --output Output url (network).
-f --file File target Output url.
--videoPid Video Pid. If not provided, 0X1F0 will be used.
--klvPid Klv Pid. If not provided, 0X1F1 will be used.
-p --packet Default Klv packet to insert. Can be either RAW Klv or Json.
-t --timeInterval Klv insertion interval (for default packet). If set to 0 (default), will be inserted with every frame.
--frameResolution Frame resolution - 'Width'x'Height'. Default 720x480.
--encodingResolution Frame resolution - 'Width'x'Height'. Default is the source resolution.
-b --bitrate Encoding bitrate (in KBit/s). Default 1000.
--framerate Frame rate. Default 30.
--encodingProfile Baseline = 0, HighProfile = 1, MainProfile = 2. Default 0 (baseline)
-v --video Show video during processing. Default - false.
--syncKlvMode SyncKlv Mode. Default - false (generates ASYNC KLV).
--licenseFile License File path. If not set, Injector will try to load KlvInjector.lic file in Application.StartupPath directory.
--licenseKey License key.
-? --help Help.

For example:

KlvInjectorEncodeApp.exe -o udp://225.1.1.1:1234 -p defaultPacket.bin

Using SDK

Let's create a VS project, add references and make sure all required dependencies are copied to the target directory.

KlvInjector related references:

  • KlvInjector
  • KlvPlayer
  • StCoreWr
  • Klv2JsonLib

Test App related references:

  • Colorful.Console
  • FluentCommanLineParser
  • Newtonsoft.Json

Next, we create an instance of the KlvInjector, initialize it and add events:

CKlvInjector m_KlvInjector = new CKlvInjector();

// Setup events
m_KlvInjector.PlayerEvent += new NotifyPlayerEvent(OnPlayerEvent);
m_KlvInjector.ErrorEvent += new NotifyError(OnErrorEvent);

There are some additional parameters that may be configured:

// Setup video / audio rendering
// Set to true if you want to decode and show the video
m_KlvInjector.RenderVideo = true;  
m_KlvInjector.RenderAudio = false;

// Set Window handle to render video to. If set to 0, a default window will be created internally.
m_KlvInjector.Hwnd = 0;

// Configure KlvInsertion mode - SYNC or ASYNC
m_klvProps = new KlvDataPropsWr(ProcessingModeWr.INSERT_KLV_SYNC);

// Read default packet, if needed
if (!string.IsNullOrEmpty(m_DefaultPcktPath))
    ReadDefaultPacket();

Next, we'll configure the output. In this demo we'll have both network and file targets, so the resulted STANAG stream will be simultaneously recorded to file and sent to the network.

// Network stream target
m_KlvInjector.NetTarget.Url = m_targetUrl;
m_KlvInjector.NetTarget.Use = true;

// File target
m_KlvInjector.FileTarget.Dir = Path.GetDirectoryName(m_targetFile);
m_KlvInjector.FileTarget.Name = Path.GetFileName(m_targetFile);
m_KlvInjector.FileTarget.SegmentationType = FileSegmentationType.SegmentationType_None;
m_KlvInjector.FileTarget.Use = true;

There are some additional parameters that can be configured but for the sake of simplicity we'll first go with defaults.

As we need to encode video, lets set the related parameters and add video pid to the output multiplex :

var rawVideoFrameProps = new RawVideoFramePropsWr();
rawVideoFrameProps.Height = 1920;
rawVideoFrameProps.Width = 1080;
rawVideoFrameProps.RawVideoFrameType = VideoFrameType.RGB24;
rawVideoFrameProps.EncodingParams.BitRate = 1024 * 1000;
rawVideoFrameProps.EncodingParams.Width = -1;  // use source Width
rawVideoFrameProps.EncodingParams.Height = -1; // use source Height
rawVideoFrameProps.EncodingParams.Profile = ProfileWr.MainProfile;
rawVideoFrameProps.EncodingParams.FrameRate = m_FrameRate;
   //rawVideoFrameProps.EncodingParams.FrameRateDenominator = 1;   
   // If you want to set frame rate of 29.97:
   // EncoderConfigParamsWr.FrameRate = 30000;
   // EncoderConfigParamsWr.FrameRateDenominator = 1001;

int m_VideoPid = 0X1F0;

Next, add Klv pid to the output multiplex :

var m_klvProps = new KlvDataPropsWr(ProcessingModeWr.INSERT_KLV_SYNC);  // We'll be using **Sync klv** that allows frame accurate synchronization of video and Klv telemetry
int m_KlvPid = 0X1F1;

Now, we just need to init and start the Injector and pump video frames accompanied with the Klv data

// Initialize injector
m_KlvInjector.Init();
// Start Processing
m_KlvInjector.Start();

// Add video and Klv pids
m_KlvInjector.AddVideoPidToOutput(m_VideoPid, rawVideoFrameProps);
m_KlvInjector.AddKlvPidToOutput(m_KlvPid, m_klvProps);

The injector is running now. We just need to send the image and the Klv metadata at the desired frame rate (like 30 fps).

m_KlvInjector.WritePacketToOutputPid(m_VideoPid, frameBmp, timestamp);
m_KlvInjector.WritePacketToOutputPid(m_KlvPid, pcktBuf, timestamp);
  • frameBmp - bitmap. The bitmap can be created dynamically, as in the sample app or taken from the stream/file, after some pre-Processing.
  • timestamp - timestamp for video and SYNC KLV. Reference clock (100-nanosecond).
  • pcktBuf - RAW Klv buffer.

Note. For Klv data you can omit the timestamp. It will be set automatically.