This document is a machine-translated draft and is currently undergoing review. Some content may be inaccurate or differ from the original Korean version. For the most precise information, refer to the Korean documentation.
Web Player Controller(formerly VG Controller) is a JavaScript library that communicates with the Kollus Player embedded via iframe on a customer's website,
enabling you to control playback state or receive real-time events.
Key features
- Unified control: Control all player types with a single specification.
- Standalone operation: Operates independently without any external library dependencies.
- Event-driven architecture: Supports method calls and real-time event listener structures.
Terminology
Definitions of key technical terms and player notation used in this document. (Learn More: Kollus Player Types)
| Term | Description |
|---|
| Video Gateway | A server that delivers playback data and authentication information upon viewer request |
| Player ID | Unique ID of the Kollus Player |
| Hardware ID | A hardware-specific unique ID provided when an identifiable value exists, such as in Windows environments |
| HLS Fragment | The minimum unit media segment file that divides the entire video during playback based on the HLS(HTTP Live Streaming) protocol |
| v3 | HTML5 Player for PC (Hybrid): A hybrid HTML5 player applied when playing encrypted content on Microsoft Edge or Chrome 45 and above |
| v4 | HTML5 Player for All: A plugin-less HTML5 player exclusively for standard content(unencrypted) |
| v5 | Web Player: A next-generation integrated web player combining the advantages of both installed and plugin-less players |
Library installation and initialization
Load the client script, then specify the control target (iframe) to create an instance.
Basic implementation example
<script src="https://file.kollus.com/vgcontroller/vg-controller-client.latest.min.js"></script>
<script>
window.onload = function () {
try {
var controller = new VgControllerClient({
target_window: document.getElementById('child').contentWindow,
});
} catch (e) {
console.error(e);
}
};
</script>
<body>
<iframe id="child" src="https://v.kr.kollus.com/{MEDIA_CONTENT_KEY}..."></iframe>
</body>
Notes
- Target specification: The
target_window property must receive the contentWindow object of the iframe element.
- Browser compatibility: This library uses the
window.postMessage API for communication. Operation is limited in browsers that do not support this API.
- Multiple player control: If multiple players (
iframe) exist on a page, a separate instance must be created for each iframe ID.
Exception codes
Error codes that may occur during initialization and communication.
| Code | Message | Description |
|---|
-1 | * | An exception that occurred during postMessage communication |
-99 | player type is not defined | Missing player type information |
-99 | player type must be one of v2, v3, v4 and flash | Unsupported player |
-99 | this browser does not support postMessage | The browser does not support the postMessage API |
-99 | listener is not callable | The event listener to be registered is not a valid function |
CDN path
Web Player Controller is provided via CDN. For the Integrity attribute (Integrity Code) by version, refer to the CDN list.
Auto-apply latest version
<script src="https://file.kollus.com/vgcontroller/vg-controller-client.latest.min.js"></script>
Pin a specific version
<script src="https://file.kollus.com/vgcontroller/vg-controller-client.1.1.4.min.js"></script>
Security hardening (sri)
It is recommended to use the SRI(Subresource Integrity) attribute to prevent library tampering.
<script src="https://file.kollus.com/vgcontroller/vg-controller-client.1.2.3.min.js"
integrity="sha256-esUCCL4RPYMS8AR+Sl3lNrFa5M+zgpt4Gb77qtz66OY="
crossorigin="anonymous">
</script>
Event listening
Use the controller.on() method to receive player state changes and playback events in real time.
Listener registration methods
Single listener
controller.on('event_name', function(param) {
});
Multiple listeners
controller.on('event_name', function(param) {
});
controller.on('event_name', function(param) {
});
Method chaining
You can implement consecutive event registration with concise code.
controller.on('event_name_1', function(param) {
}).on('event_name_2', function(param) {
});
Due to the nature of the JavaScript asynchronous environment, the execution order of multiple listeners registered for the same event is not guaranteed.
- Recommendation: Write logic that requires a strict execution order sequentially within a single listener.
Event list
Playback status events
| Event | Description | Target player |
|---|
loaded | Fired when the player components have finished loading | v3, v4, v5 |
ready | Fired when playback data has been received from the server and the player is ready to play | v3, v4, v5 |
play | Fired when playback starts for the first time or resumes after being paused | v3, v4, v5 |
pause | Fired when playback is paused | v3, v4, v5 |
done | Fired when the playback position reaches the end of the total length (duration) | v3, v4, v5 |
waiting | Fired at 1-second intervals until recovery when additional buffering is required due to network conditions | v4, v5 |
Progress events
Depending on HTML5 browser performance and network conditions, the progress event may have a margin of approximately 0.1–0.5 seconds rather than firing at exactly 1-second intervals.
| Event | Description | Target player |
|---|
progress | Fired at approximately 1-second intervals during playback, delivering the current playback position | v3, v4, v5 |
Progress parameter details
| Parameter | Type | Description |
|---|
percent | integer | Current playback progress (0–100) |
position | number | Current playback position (sec) |
duration | number | Total content duration (sec) |
controller.on('progress', function(percent, position, duration) {
console.log(percent + '%', position + 'sec');
});
Seek events
| Event | Description | Target player |
|---|
seeking | Fired when the user starts moving the playback position | v4, v5 |
seeked | Fired when the playback position move is complete | v4, v5 |
seek_start | Fired at the first moment a playback position move is detected | v4, v5 |
Audio events
| Event | Description | Target player |
|---|
muted | Fired when the mute state (On/Off) changes | v3, v4, v5 |
volumechange | Fired when the volume level changes | v3, v4, v5 |
Muted parameter details
| Parameter | Type | Description |
|---|
is_muted | boolean | true: Mute appliedfalse: Mute released
|
Volumechange parameter details
| Parameter | Type | Description |
|---|
volume | integer | Changed volume level (0–100) |
playback speed events
| Event | Description | Target player |
|---|
speedchange | Fired when the playback speed changes | v3, v4, v5 |
playbackrateschange | Fired when the available playback speed group changes | v3, v4, v5 |
Speedchange parameter details
| Parameter | Type | Description |
|---|
speed | string | Changed playback speed (0.5–4) |
Screen events
| Event | Description | Target player |
|---|
screenchange | Fired when switching between fullscreen mode and normal mode | v3, v4, v5 |
device_orientation_changed | Fired when the mobile screen orientation (landscape/portrait) changes | v4, v5 |
user_active_changed | Fired when the control bar activation/deactivation state changes due to user interaction | v4, v5 |
Screenchange parameter details
| Parameter | Type | Description |
|---|
screen | string | windowed: Normal modefullscreen: Fullscreen mode
|
Device_orientation_changed parameter details
| Parameter | Type | Description |
|---|
orientation | string | Portrait: Portrait orientationLandscape: Landscape orientation
|
Subtitle events
| Event | Description | Target player |
|---|
subtitle_load_done | Fired when the subtitle file has finished loading | v3, v4, v5 |
subtitlevisibilitychange | Fired when the subtitle visibility state (On/Off) changes | v3, v4, v5 |
Streaming events
| Event | Description | Target player |
|---|
hls_manifest_loaded | Fired when the HLS manifest file finishes loading | v4, v5 |
dash_manifest_loaded | Fired when the DASH manifest file finishes loading | v4, v5 |
bitrate_data_loaded | Fired when bitrate data finishes loading (sorted in ascending order) | v4, v5 |
hlsfragchange | Fired when an HLS Fragment changes | v4, v5 |
controller.on('bitrate_data_loaded', function(bitrate_data) {
});
Other events
| Event | Description | Target player |
|---|
error | Called when a system error occurs during playback | v3, v4, v5 |
html5_video_supported | Called when checking whether the browser supports HTML5 Video | v3, v4, v5 |
jumpstepchange | Fired when the time unit for seek (fast-forward/rewind) changes | v3, v4, v5 |
bookmark_change | Fired when a bookmark is added, updated, or deleted | v3 |
next_episode_auto_change | Fired when the auto-play next episode setting changes | v3, v4, v5 |
next_episode_requested | Fired when a next episode callback is requested | v3, v4, v5 |
picture_in_picture_entered | Fired when PIP(Picture-in-Picture) mode is entered | v3, v4, v5 |
picture_in_picture_leaved | Fired when PIP mode is exited | v3, v4, v5 |
chapter_data_change | Fired when chapter data changes | v5 |
Method usage
You can directly control the player's behavior using the object created through the Controller instance.
Basic call method
Control commands that do not require separate arguments call the method directly.
Parameter passing method
Control commands that require configuration values pass parameters as method arguments.
controller.set_volume(90);
Method list
Event listener methods
| Method | Description | Target player |
|---|
on(event_name, callback) | Register an event listener- Parameters
event_name (string): event namecallback (function): function to be called when the event is fired
- Return value:
VgControllerClient instance
| v3, v4, v5 |
off(event_name) | Remove all listeners registered for a specific event at once- Parameters
event_name (string): event name
| v3, v4, v5 |
Playback methods
| Method | Description | Target player |
|---|
play([start_at]) | Start playback- Parameters (Optional)
start_at (integer, sec): Start playback immediately from the specified position
- Call examples
- Start playback:
controller.play(); - Play from 10 seconds:
controller.play(10);
| v3, v4, v5 |
pause() | Pause the currently playing content | v3, v4, v5 |
toggle_pip() | Toggle PIP(Picture-in-Picture) mode activation state | v3, v4, v5 |
get_progress() | Return current playback information (percent, position, duration) | v3, v4, v5 |
Seek methods
| Method | Description | Target player |
|---|
ff() | Move forward by the jumpstep value set with the set_jumpstep method from the current playback position (fast forward, default: 10 seconds) | v3, v4, v5 |
rw() | Move backward by the jumpstep value set with the set_jumpstep method from the current playback position (rewind, default: 10 seconds) | v3, v4, v5 |
set_current_time(time) | Move to the specified position while maintaining the current playback state- Parameters
time (integer, sec): position to move to
| v3, v4, v5 |
get_current_time() | Return the current playback position | v3, v4, v5 |
set_jumpstep(jumpstep) | Set the time interval to move when ff() or rw() is called- Parameters
jumpstep (integer, sec): time interval to move
| v3, v4, v5 |
get_jumpstep() | Return the currently configured jumpstep value | v3, v4, v5 |
set_keyframe_seek_default(is_default) | Set keyframe-based seeking as the default- Parameters
is_default (boolean): whether to set as default
| v2 |
Comparison: play([start_at]) vs set_current_time(time)
play(10): Move to the 10-second position and start playback immediately
set_current_time(10): Move to the 10-second position, but maintain the current play/pause state
Audio methods
| Method | Description | Target player |
|---|
set_volume(volume) | Set volume- Parameters
volume (integer, 0~100): volume to set
| v3, v4, v5 |
get_volume() | Return the current volume level | v3, v4, v5 |
mute() | Toggle mute state (On/Off) | v3, v4, v5 |
Screen methods
| Method | Description | Target player |
|---|
set_screen() | Toggle between fullscreen mode and normal mode (not supported in Firefox) | v3, v4, v5 |
get_screen() | Return the current screen mode- Return value
windowed: Normal modefullscreen: Fullscreen mode
| v3, v4, v5 |
set_fullscreen_element(element) | Set the DOM element to target when switching to fullscreen- Parameters
element (string): HTML element to use as the fullscreen target
| v3, v4, v5 |
enable_fullscreen_button() | Enable the fullscreen toggle button in the player UI | v3, v4, v5 |
set_video_visibility(visibility) | Show or hide the video display (audio playback continues)visibility parameter details
| v3, v4, v5 |
get_video_visibility() | Return the current visibility state of the video display | v3, v4, v5 |
set_ratio(type) | Set the screen zoom and aspect ratio modetype parameter detailscontain: Fit within the screen while maintaining the aspect ratiofill: Fill the entire screen regardless of aspect ratioenlargement: Fit based on the vertical height (horizontal scrolling may occur)
| v3, v4, v5 |
Control bar methods
| Method | Description | Target player |
|---|
set_control_visibility(visibility) | Set whether the built-in control bar is visible | v3, v4, v5 |
get_control_visibility() | Return the current visibility state of the built-in control bar | v3, v4, v5 |
set_controls_inactive_time(time) | Set the auto-hide wait time for the control bar (0: always visible) | v3, v4, v5 |
get_controls_inactive_time() | Return the configured auto-hide wait time for the control bar | v3, v4, v5 |
set_controls_activity(activity) | Set whether the control bar is active | v3, v4, v5 |
get_controls_activity() | Return the activation state of the control bar | v3, v4, v5 |
set_controlbar_progress_only(enable) | Show only the progress bar and hide all other control buttons | v3, v4, v5 |
get_controlbar_progress_only() | Return whether the progress bar is shown exclusively | v3, v4, v5 |
set_controlbar_hide_playing(enable) | Set whether the control bar is automatically hidden during playback | v4, v5 |
get_controlbar_hide_playing() | Return whether the control bar auto-hide during playback is enabled | v4, v5 |
hide_controlbar_button(value) | Hide a button from the control bar (recommended to call after the ready event)value parameter detailsplay: playrewind: rewindforward: fast forwardrepeat: loop sectioncurrenttime: current playback timedurationtime: total playback timequality: video qualityplaybackrate: playback speedmute: mutevolume: volume graphsubtitle: subtitlesetting: settingsfullscreen: full screen modechat: chattingpip: PIP modebigplay: center play button (Kollus Web Player)seekcontainer: mobile left/right rewind/fast forward (Kollus Web Player)
| v3, v4, v5 |
set_setting_panel_activity(activity) | Set whether to display the settings panel and specify the panelactivity parameter detailstrue: showfalse: hidepanel name: show the panel with the specified name
| v3, v4, v5 |
Hides the full screen mode and settings buttons from the control bar.
controller.hide_controlbar_button(['fullscreen', 'setting']);
playback speed methods
| Method | Description | Target player |
|---|
set_speed(speed) | Set playback speed in increments of 0.1 within the range of 0.5–4 | v3, v4, v5 |
get_speed() | Return the currently applied playback speed as a string | v3, v4, v5 |
set_playback_rates(rates) | Set the playback speed group displayed in the player UI (refer to the method call example below) | v3, v4, v5 |
get_playback_rates() | Return the currently configured playback speed group as a string | v3, v4, v5 |
Set_playback_rates method call examples
Single array: Configure playback speed options in a single row.
controller.set_playback_rates([0.5, 1, 1.5, 2]);
Double array: [playback speed array, number of rows to display]
controller.set_playback_rates([[0.5, 1, 1.5, 2, 3, 4], 2]);
When watching via HLS on iOS, only up to 2x playback speed is supported due to OS policies and technical specifications.
loop section methods
| Method | Description | Target player |
|---|
set_repeat_start([position]) | Sets the loop section start point (if the argument is omitted, the current playback position is used) | v3, v4, v5 |
set_repeat_end([position]) | Sets the loop section end point (if the argument is omitted, the current playback position is used) | v3, v4, v5 |
unset_repeat() | Deactivates the active loop section setting and switches to normal playback mode | v3, v4, v5 |
get_repeat() | Returns the current loop section status information (status, start, end) | v3, v4, v5 |
Set_repeat method call examples
Sets the 10-second point as the loop start point.
controller.set_repeat_start(10);
Sets the 20-second point as the loop end point.
controller.set_repeat_end(20);
Bookmark methods
| Method | Description | Target player |
|---|
refresh_bookmark() | Synchronizes and updates the latest bookmark list from the server | v3, v4, v5 |
get_bookmark_count() | Returns the number of all bookmarks, official bookmarks, and my bookmarks (all, index, user) | v3, v4, v5 |
set_bookmark_add_activity(activation) | Sets whether the add bookmark button is enabled | v3, v4, v5 |
set_bookmark_update_activity(activation) | Sets whether the edit bookmark button is enabled | v3, v4, v5 |
The set_bookmark_add_visibility and set_bookmark_update_visibility methods are no longer supported. Use the activation series methods listed in the table above.
Subtitle methods
| Method | Description | Target player |
|---|
set_subtitle(value) | Directly set subtitle data (VTT URL or RawData) | v3, v4, v5 |
set_subtitle_visibility(visibility) | Set main subtitle visibility | v3, v4, v5 |
set_subtitle_sub_visibility(visibility) | Set sub subtitle visibility | v3, v4, v5 |
set_subtitle_shadow_rect(is_rect) | Set subtitle background style | v3, v4, v5 |
get_subtitle_shadow_rect() | Return the current subtitle background style value | v3, v4, v5 |
set_subtitle_font_size(size) | Set subtitle text size (px) | v3, v4, v5 |
get_subtitle_font_size() | Return the current subtitle text size | v3, v4, v5 |
set_subtitle_activity(activity) | Set subtitle display position | v3, v4, v5 |
get_subtitle_activity() | Return subtitle display position | v3, v4, v5 |
get_subtitles_list() | Return the full main subtitle list | v3, v4, v5 |
get_subtitles_sub_list() | Return the full sub subtitle list | v3, v4, v5 |
set_current_subtitle(index) | Switch to the main subtitle at the specified index | v3, v4, v5 |
set_current_subtitle_sub(index) | Switch to the sub subtitle at the specified index | v3, v4, v5 |
Chapter methods
| Method | Description | Target player |
|---|
set_chapter_data(data) | Set chapter data | v5 |
get_chapter_data() | Return the currently configured chapter data | v5 |
The data parameter of set_chapter_data(data) only accepts URL String or JSON format.
When chapter data is changed, the Other events event is fired.
controller.set_chapter_data('https://example.com/chapters.json');
controller.set_chapter_data({
"ko": [
{
"position": 0,
"value": "first"
},
{
"position": 30,
"value": "second"
}
],
"default_language_code": "ko"
});
Bitrate methods
| Method | Description | Target player |
|---|
set_bitrate(index) | Switch to the bitrate at the specified index. When requesting an actual change with the set_bitrate() method, you must pass the array index +1 as the argument. (0: auto) | v4, v5 |
get_bitrate_data() | Return the list of available bitrates. The index of the array returned by get_bitrate_data() starts at 0. | v4, v5 |
| Method | Description | Target player |
|---|
get_player_id() | Returns the Kollus Player ID (can be called after the ready event) | v3, v4, v5 |
get_hardware_id() | Returns the hardware ID (can be called after the ready event) | v3 |
get_player_type() | Returns the type of player currently running- Return value
v3: HTML5 Player for PC (Hybrid)v4: HTML5 Player for All
| v3, v4, v5 |
get_video_info() | Returns content resolution and bitrate information (width, height, bitrate) (can be called after the ready event) | v3, v4, v5 |
get_lms_data() | Returns Learning Management System(LMS) integration data | v3, v4, v5 |
get_hls_frag_data() | Returns HLS Fragment-related data | v4, v5 |
dispose() | Removes the player instance | v4, v5 |
Custom skin methods
| Method | Description | Target player |
|---|
get_custom_skin() | Returns the custom skin settings (JSON) currently applied to the player (can be called after the ready event) | v4, v5 |
set_custom_skin(json_data) | Changes the custom skin by injecting JSON-format settings data (can be called after the ready event) | v4, v5 |
Set_custom_skin method call example
controller.set_custom_skin({
controlbar: {
enable: true,
backgroundColor: 123123,
backgroundAlpha: 0.2,
progressButton: {
enable: false
}
}
});
Error methods
| Method | Description | Target player |
|---|
get_error_detail() | Returns detailed information (code, message, param) about the current error | v3, v4, v5 |
set_custom_error(code, message, param) | Displays developer-defined custom error codes and messages in the player UI instead of the default error screen | v3, v4, v5 |
Chat methods
| Method | Description | Target player |
|---|
set_chat_config(value) | Apply chat-related settings (recommended to call after the ready event) | v3, v4, v5 |
notify_visibleheight_changed(height) | Pass the screen height change value caused by keyboard activation in Android WebView environments | v3, v4, v5 |
Set_chat_config method call example
controller.set_chat_config({
customer_page: [{
title: 'Class Title',
url: 'https://example.com'
}]
});
- Security policy: Only URLs with the https protocol are allowed when injecting external pages.
- Script restrictions:
script tags within content passed via the html attribute are restricted from execution for security reasons.
Close event methods
| Method | Description | Target player |
|---|
set_enable_close_event() | Activate browser close (close) detection and callback feature | v3, v4, v5 |
set_close_callback_fn(fn) | Register a custom callback function to execute when the browser is closed | v3, v4, v5 |
get_enable_close_event() | Return whether the browser close (close) callback is activated | v3, v4, v5 |
set_close_button(enable, fn) | Create a mobile close button and configure the click event (recommended to call after the ready event) | v4, v5 |
Other methods
| Method | Description | Target player |
|---|
set_vr_overlay(options) | Configure permission request overlay for VR content playback in iOS environments | v3, v4, v5 |
debug() | Output player debug log data to the console | v5 |
set_short_key(enable) | Enable or disable player shortcuts | v2 |
get_topmost() | Return whether the player window is set to display on top | v2 |
set_topmost(topmost) | Set whether the player window is displayed on top | v2 |
set_lms_check() | Configure LMS data transfer completion check when the browser closes | v2 |
Notes for mobile vr content playback
Due to security policies in mobile browsers and technical constraints of the iframe environment, the following points must be confirmed when playing VR(360°) content.
- Android: Due to
orientation data synchronization issues within iframe, the left/right control direction of VR video may operate in the opposite direction from the actual device movement.
- iOS: Starting from iOS 13, user approval is required to access
DeviceMotion (accelerometer/gyro) data for enhanced security. However, due to browser security policies, permission request popups cannot be triggered inside an iframe, causing VR control functionality to not work.
Solution
- Use VG Controller version 1.1.10 or higher.
- In iOS environments, you must call the
set_vr_overlay() method.
var controller = new VgControllerClient({
target_window: player.contentWindow
});
controller.set_vr_overlay({
target_element: document.getElementById('player'),
permission_request_help_message: 'Please allow access to the accelerometer and gyroscope sensors to use VR features.'
});
For iOS 13.4 and above, the rotationRate value of the DeviceMotion API is not returned correctly due to Apple's privacy policy.