rx-player 3.33.0 → 3.33.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +13 -0
- package/VERSION +1 -1
- package/dist/_esm5.processed/core/api/public_api.js +2 -2
- package/dist/_esm5.processed/manifest/manifest.js +1 -0
- package/dist/_esm5.processed/utils/retry_promise_with_backoff.d.ts +11 -0
- package/dist/_esm5.processed/utils/retry_promise_with_backoff.js +18 -4
- package/dist/mpd-parser.wasm +0 -0
- package/dist/rx-player.d.ts +1 -1
- package/dist/rx-player.js +24 -9
- package/dist/rx-player.min.d.ts +1 -1
- package/dist/rx-player.min.js +1 -1
- package/package.json +6 -6
- package/.editorconfig +0 -22
- package/.eslintrc.js +0 -406
- package/.github/workflows/checks.yml +0 -101
- package/.github/workflows/perfs.yml +0 -22
- package/.github/workflows/sonarcloud_analysis.yml +0 -20
- package/CONTRIBUTING.md +0 -272
- package/FILES.md +0 -283
- package/jest.config.js +0 -73
- package/manifest.mpd +0 -149
- package/scripts/README.md +0 -11
- package/scripts/build/constants.d.ts +0 -53
- package/scripts/build/generate_build.js +0 -190
- package/scripts/build/templates/experimental/features/index.d.ts +0 -16
- package/scripts/build/templates/experimental/features/index.js +0 -16
- package/scripts/build/templates/experimental/index.d.ts +0 -16
- package/scripts/build/templates/experimental/index.js +0 -16
- package/scripts/build/templates/experimental/tools/VideoThumbnailLoader/index.d.ts +0 -18
- package/scripts/build/templates/experimental/tools/VideoThumbnailLoader/index.js +0 -18
- package/scripts/build/templates/experimental/tools/index.d.ts +0 -16
- package/scripts/build/templates/experimental/tools/index.js +0 -16
- package/scripts/build/templates/features/index.d.ts +0 -16
- package/scripts/build/templates/features/index.js +0 -16
- package/scripts/build/templates/logger/index.d.ts +0 -17
- package/scripts/build/templates/logger/index.js +0 -17
- package/scripts/build/templates/minimal/index.d.ts +0 -17
- package/scripts/build/templates/minimal/index.js +0 -17
- package/scripts/build/templates/tools/TextTrackRenderer.d.ts +0 -18
- package/scripts/build/templates/tools/TextTrackRenderer.js +0 -18
- package/scripts/build/templates/tools/index.d.ts +0 -16
- package/scripts/build/templates/tools/index.js +0 -16
- package/scripts/build/templates/tools/string-utils.d.ts +0 -18
- package/scripts/build/templates/tools/string-utils.js +0 -18
- package/scripts/build/templates/types/index.d.ts +0 -16
- package/scripts/build/templates/types/index.js +0 -15
- package/scripts/canal-release.patch +0 -316
- package/scripts/check_nodejs_import_compatibility.js +0 -60
- package/scripts/deploy_new_demo +0 -123
- package/scripts/fast_demo_build.js +0 -129
- package/scripts/generate_certificate +0 -19
- package/scripts/generate_demo_list.js +0 -105
- package/scripts/generate_documentation_list.js +0 -109
- package/scripts/generate_full_demo.js +0 -201
- package/scripts/generate_standalone_demo.js +0 -82
- package/scripts/launch_static_server.js +0 -163
- package/scripts/list-npm-scripts.js +0 -207
- package/scripts/make-dev-releases +0 -90
- package/scripts/report_build_sizes +0 -96
- package/scripts/run_standalone_demo.js +0 -27
- package/scripts/start_demo_web_server.js +0 -44
- package/scripts/update-version +0 -48
- package/scripts/update_gh-pages_demo +0 -132
- package/scripts/update_gh-pages_doc +0 -106
- package/scripts/utils/display_webpack_errors.js +0 -33
- package/scripts/utils/get_human_readable_hours.js +0 -14
- package/scripts/wasm-strip.js +0 -359
- package/sonar-project.properties +0 -7
- package/src/README.md +0 -136
- package/src/compat/README.md +0 -29
- package/src/compat/__tests__/add_text_track.test.ts +0 -176
- package/src/compat/__tests__/browser_compatibility_types.test.ts +0 -152
- package/src/compat/__tests__/browser_version.test.ts +0 -84
- package/src/compat/__tests__/can_patch_isobmff.test.ts +0 -50
- package/src/compat/__tests__/can_rely_on_video_visibility_and_size.test.ts +0 -78
- package/src/compat/__tests__/can_reuse_media_keys.test.ts +0 -31
- package/src/compat/__tests__/change_source_buffer_type.test.ts +0 -60
- package/src/compat/__tests__/clear_element_src.test.ts +0 -252
- package/src/compat/__tests__/enable_audio_track.test.ts +0 -341
- package/src/compat/__tests__/fullscreen.test.ts +0 -286
- package/src/compat/__tests__/is_codec_supported.test.ts +0 -78
- package/src/compat/__tests__/is_offline.test.ts +0 -65
- package/src/compat/__tests__/is_seeking_approximate.test.ts +0 -48
- package/src/compat/__tests__/is_vtt_cue.test.ts +0 -71
- package/src/compat/__tests__/make_vtt_cue.test.ts +0 -97
- package/src/compat/__tests__/patch_webkit_source_buffer.test.ts +0 -144
- package/src/compat/__tests__/remove_cue.test.ts +0 -229
- package/src/compat/__tests__/should_favour_custom_safari_EME.test.ts +0 -128
- package/src/compat/__tests__/should_reload_media_source_on_decipherability_update.test.ts +0 -50
- package/src/compat/__tests__/should_renew_media_key_system_access.test.ts +0 -55
- package/src/compat/__tests__/should_unset_media_keys.test.ts +0 -53
- package/src/compat/__tests__/should_validate_metadata.test.ts +0 -53
- package/src/compat/__tests__/should_wait_for_data_before_loaded.test.ts +0 -121
- package/src/compat/__tests__/should_wait_for_have_enough_data.test.ts +0 -36
- package/src/compat/add_class_name.ts +0 -41
- package/src/compat/add_text_track.ts +0 -58
- package/src/compat/browser_compatibility_types.ts +0 -222
- package/src/compat/browser_detection.ts +0 -172
- package/src/compat/browser_version.ts +0 -44
- package/src/compat/can_patch_isobmff.ts +0 -30
- package/src/compat/can_rely_on_video_visibility_and_size.ts +0 -52
- package/src/compat/can_reuse_media_keys.ts +0 -20
- package/src/compat/change_source_buffer_type.ts +0 -66
- package/src/compat/clear_element_src.ts +0 -55
- package/src/compat/eme/close_session.ts +0 -111
- package/src/compat/eme/constants.ts +0 -21
- package/src/compat/eme/custom_key_system_access.ts +0 -67
- package/src/compat/eme/custom_media_keys/ie11_media_keys.ts +0 -186
- package/src/compat/eme/custom_media_keys/index.ts +0 -28
- package/src/compat/eme/custom_media_keys/moz_media_keys_constructor.ts +0 -88
- package/src/compat/eme/custom_media_keys/ms_media_keys_constructor.ts +0 -69
- package/src/compat/eme/custom_media_keys/old_webkit_media_keys.ts +0 -235
- package/src/compat/eme/custom_media_keys/types.ts +0 -67
- package/src/compat/eme/custom_media_keys/webkit_media_keys.ts +0 -308
- package/src/compat/eme/custom_media_keys/webkit_media_keys_constructor.ts +0 -50
- package/src/compat/eme/eme-api-implementation.ts +0 -318
- package/src/compat/eme/generate_key_request.ts +0 -162
- package/src/compat/eme/get_init_data.ts +0 -159
- package/src/compat/eme/get_uuid_kid_from_keystatus_kid.ts +0 -37
- package/src/compat/eme/get_webkit_fairplay_initdata.ts +0 -75
- package/src/compat/eme/index.ts +0 -47
- package/src/compat/eme/load_session.ts +0 -67
- package/src/compat/enable_audio_track.ts +0 -33
- package/src/compat/event_listeners.ts +0 -566
- package/src/compat/fullscreen.ts +0 -87
- package/src/compat/get_start_date.ts +0 -48
- package/src/compat/has_issues_with_high_media_source_duration.ts +0 -27
- package/src/compat/index.ts +0 -87
- package/src/compat/is_codec_supported.ts +0 -40
- package/src/compat/is_debug_mode_enabled.ts +0 -12
- package/src/compat/is_node.ts +0 -18
- package/src/compat/is_offline.ts +0 -44
- package/src/compat/is_seeking_approximate.ts +0 -32
- package/src/compat/is_vtt_cue.ts +0 -30
- package/src/compat/make_vtt_cue.ts +0 -51
- package/src/compat/on_height_width_change.ts +0 -119
- package/src/compat/patch_webkit_source_buffer.ts +0 -89
- package/src/compat/remove_cue.ts +0 -64
- package/src/compat/should_favour_custom_safari_EME.ts +0 -34
- package/src/compat/should_prevent_seeking_at_0_initially.ts +0 -19
- package/src/compat/should_reload_media_source_on_decipherability_update.ts +0 -32
- package/src/compat/should_renew_media_key_system_access.ts +0 -26
- package/src/compat/should_unset_media_keys.ts +0 -27
- package/src/compat/should_validate_metadata.ts +0 -27
- package/src/compat/should_wait_for_data_before_loaded.ts +0 -35
- package/src/compat/should_wait_for_have_enough_data.ts +0 -17
- package/src/config.ts +0 -32
- package/src/core/README.md +0 -56
- package/src/core/adaptive/README.md +0 -147
- package/src/core/adaptive/__tests__/buffer_based_chooser.test.ts +0 -548
- package/src/core/adaptive/adaptive_representation_selector.ts +0 -916
- package/src/core/adaptive/buffer_based_chooser.ts +0 -264
- package/src/core/adaptive/guess_based_chooser.ts +0 -309
- package/src/core/adaptive/index.ts +0 -45
- package/src/core/adaptive/network_analyzer.ts +0 -419
- package/src/core/adaptive/utils/__tests__/bandwith_estimator.test.ts +0 -134
- package/src/core/adaptive/utils/__tests__/ewma.test.ts +0 -79
- package/src/core/adaptive/utils/__tests__/filter_by_bitrate.test.ts +0 -56
- package/src/core/adaptive/utils/__tests__/filter_by_width.test.ts +0 -60
- package/src/core/adaptive/utils/__tests__/get_buffer_levels.test.ts +0 -48
- package/src/core/adaptive/utils/__tests__/select_optimal_representation.test.ts +0 -243
- package/src/core/adaptive/utils/bandwidth_estimator.ts +0 -88
- package/src/core/adaptive/utils/ewma.ts +0 -59
- package/src/core/adaptive/utils/filter_by_bitrate.ts +0 -46
- package/src/core/adaptive/utils/filter_by_width.ts +0 -49
- package/src/core/adaptive/utils/get_buffer_levels.ts +0 -50
- package/src/core/adaptive/utils/last_estimate_storage.ts +0 -79
- package/src/core/adaptive/utils/pending_requests_store.ts +0 -147
- package/src/core/adaptive/utils/representation_score_calculator.ts +0 -168
- package/src/core/adaptive/utils/select_optimal_representation.ts +0 -54
- package/src/core/api/README.md +0 -36
- package/src/core/api/__tests__/option_utils.test.ts +0 -1668
- package/src/core/api/__tests__/public_api.test.ts +0 -857
- package/src/core/api/__tests__/utils.test.ts +0 -195
- package/src/core/api/debug/buffer_graph.ts +0 -244
- package/src/core/api/debug/buffer_size_graph.ts +0 -130
- package/src/core/api/debug/constants.ts +0 -2
- package/src/core/api/debug/index.ts +0 -3
- package/src/core/api/debug/modules/general_info.ts +0 -213
- package/src/core/api/debug/modules/segment_buffer_content.ts +0 -155
- package/src/core/api/debug/modules/segment_buffer_size.ts +0 -48
- package/src/core/api/debug/render.ts +0 -40
- package/src/core/api/debug/utils.ts +0 -103
- package/src/core/api/index.ts +0 -27
- package/src/core/api/option_utils.ts +0 -700
- package/src/core/api/playback_observer.ts +0 -994
- package/src/core/api/public_api.ts +0 -3247
- package/src/core/api/tracks_management/__tests__/media_element_track_choice_manager.test.ts +0 -184
- package/src/core/api/tracks_management/media_element_track_choice_manager.ts +0 -975
- package/src/core/api/tracks_management/track_choice_manager.ts +0 -1280
- package/src/core/api/utils.ts +0 -216
- package/src/core/decrypt/README.md +0 -22
- package/src/core/decrypt/__tests__/__global__/get_license.test.ts +0 -422
- package/src/core/decrypt/__tests__/__global__/init_data.test.ts +0 -677
- package/src/core/decrypt/__tests__/__global__/media_key_system_access.test.ts +0 -528
- package/src/core/decrypt/__tests__/__global__/media_keys.test.ts +0 -343
- package/src/core/decrypt/__tests__/__global__/server_certificate.test.ts +0 -264
- package/src/core/decrypt/__tests__/__global__/utils.ts +0 -491
- package/src/core/decrypt/attach_media_keys.ts +0 -121
- package/src/core/decrypt/clear_on_stop.ts +0 -47
- package/src/core/decrypt/content_decryptor.ts +0 -1246
- package/src/core/decrypt/create_or_load_session.ts +0 -133
- package/src/core/decrypt/create_session.ts +0 -214
- package/src/core/decrypt/dispose_decryption_resources.ts +0 -54
- package/src/core/decrypt/find_key_system.ts +0 -376
- package/src/core/decrypt/get_key_system_configuration.ts +0 -51
- package/src/core/decrypt/get_media_keys.ts +0 -147
- package/src/core/decrypt/index.ts +0 -36
- package/src/core/decrypt/init_media_keys.ts +0 -60
- package/src/core/decrypt/session_events_listener.ts +0 -386
- package/src/core/decrypt/set_server_certificate.ts +0 -105
- package/src/core/decrypt/types.ts +0 -404
- package/src/core/decrypt/utils/__tests__/are_init_values_compatible.test.ts +0 -261
- package/src/core/decrypt/utils/__tests__/clean_old_loaded_sessions.test.ts +0 -158
- package/src/core/decrypt/utils/__tests__/clean_old_stored_persistent_info.test.ts +0 -133
- package/src/core/decrypt/utils/are_init_values_compatible.ts +0 -140
- package/src/core/decrypt/utils/check_key_statuses.ts +0 -193
- package/src/core/decrypt/utils/clean_old_loaded_sessions.ts +0 -45
- package/src/core/decrypt/utils/clean_old_stored_persistent_info.ts +0 -48
- package/src/core/decrypt/utils/get_drm_system_id.ts +0 -42
- package/src/core/decrypt/utils/init_data_values_container.ts +0 -119
- package/src/core/decrypt/utils/is_session_usable.ts +0 -62
- package/src/core/decrypt/utils/key_id_comparison.ts +0 -57
- package/src/core/decrypt/utils/key_session_record.ts +0 -174
- package/src/core/decrypt/utils/loaded_sessions_store.ts +0 -505
- package/src/core/decrypt/utils/media_keys_infos_store.ts +0 -85
- package/src/core/decrypt/utils/persistent_sessions_store.ts +0 -358
- package/src/core/decrypt/utils/serializable_bytes.ts +0 -59
- package/src/core/decrypt/utils/server_certificate_store.ts +0 -133
- package/src/core/fetchers/README.md +0 -84
- package/src/core/fetchers/cdn_prioritizer.ts +0 -207
- package/src/core/fetchers/index.ts +0 -38
- package/src/core/fetchers/manifest/index.ts +0 -28
- package/src/core/fetchers/manifest/manifest_fetcher.ts +0 -798
- package/src/core/fetchers/segment/__tests__/task_prioritizer.test.ts +0 -763
- package/src/core/fetchers/segment/index.ts +0 -28
- package/src/core/fetchers/segment/prioritized_segment_fetcher.ts +0 -113
- package/src/core/fetchers/segment/segment_fetcher.ts +0 -482
- package/src/core/fetchers/segment/segment_fetcher_creator.ts +0 -129
- package/src/core/fetchers/segment/task_prioritizer.ts +0 -455
- package/src/core/fetchers/utils/error_selector.ts +0 -38
- package/src/core/fetchers/utils/schedule_request.ts +0 -493
- package/src/core/init/README.md +0 -81
- package/src/core/init/directfile_content_initializer.ts +0 -310
- package/src/core/init/index.ts +0 -22
- package/src/core/init/media_source_content_initializer.ts +0 -878
- package/src/core/init/types.ts +0 -266
- package/src/core/init/utils/__tests__/are_same_stream_events.test.ts +0 -84
- package/src/core/init/utils/__tests__/refresh_scheduled_events_list.test.ts +0 -94
- package/src/core/init/utils/content_time_boundaries_observer.ts +0 -646
- package/src/core/init/utils/create_media_source.ts +0 -139
- package/src/core/init/utils/create_stream_playback_observer.ts +0 -132
- package/src/core/init/utils/end_of_stream.ts +0 -108
- package/src/core/init/utils/get_initial_time.ts +0 -165
- package/src/core/init/utils/get_loaded_reference.ts +0 -82
- package/src/core/init/utils/initial_seek_and_play.ts +0 -237
- package/src/core/init/utils/initialize_content_decryption.ts +0 -172
- package/src/core/init/utils/media_source_duration_updater.ts +0 -349
- package/src/core/init/utils/rebuffering_controller.ts +0 -642
- package/src/core/init/utils/stream_events_emitter/are_same_stream_events.ts +0 -42
- package/src/core/init/utils/stream_events_emitter/index.ts +0 -22
- package/src/core/init/utils/stream_events_emitter/refresh_scheduled_events_list.ts +0 -74
- package/src/core/init/utils/stream_events_emitter/stream_events_emitter.ts +0 -252
- package/src/core/init/utils/stream_events_emitter/types.ts +0 -46
- package/src/core/init/utils/throw_on_media_error.ts +0 -74
- package/src/core/segment_buffers/README.md +0 -219
- package/src/core/segment_buffers/garbage_collector.ts +0 -177
- package/src/core/segment_buffers/implementations/audio_video/audio_video_segment_buffer.ts +0 -650
- package/src/core/segment_buffers/implementations/audio_video/index.ts +0 -18
- package/src/core/segment_buffers/implementations/image/image_segment_buffer.ts +0 -152
- package/src/core/segment_buffers/implementations/image/index.ts +0 -18
- package/src/core/segment_buffers/implementations/index.ts +0 -20
- package/src/core/segment_buffers/implementations/text/html/__tests__/utils.test.ts +0 -343
- package/src/core/segment_buffers/implementations/text/html/html_text_segment_buffer.ts +0 -527
- package/src/core/segment_buffers/implementations/text/html/index.ts +0 -24
- package/src/core/segment_buffers/implementations/text/html/parsers.ts +0 -49
- package/src/core/segment_buffers/implementations/text/html/text_track_cues_store.ts +0 -391
- package/src/core/segment_buffers/implementations/text/html/types.ts +0 -23
- package/src/core/segment_buffers/implementations/text/html/update_proportional_elements.ts +0 -93
- package/src/core/segment_buffers/implementations/text/html/utils.ts +0 -139
- package/src/core/segment_buffers/implementations/text/native/index.ts +0 -19
- package/src/core/segment_buffers/implementations/text/native/native_text_segment_buffer.ts +0 -340
- package/src/core/segment_buffers/implementations/text/native/parsers.ts +0 -47
- package/src/core/segment_buffers/implementations/types.ts +0 -386
- package/src/core/segment_buffers/implementations/utils/manual_time_ranges.ts +0 -80
- package/src/core/segment_buffers/index.ts +0 -67
- package/src/core/segment_buffers/inventory/buffered_history.ts +0 -131
- package/src/core/segment_buffers/inventory/index.ts +0 -30
- package/src/core/segment_buffers/inventory/segment_inventory.ts +0 -1111
- package/src/core/segment_buffers/inventory/types.ts +0 -35
- package/src/core/segment_buffers/segment_buffers_store.ts +0 -383
- package/src/core/stream/README.md +0 -59
- package/src/core/stream/adaptation/adaptation_stream.ts +0 -378
- package/src/core/stream/adaptation/index.ts +0 -20
- package/src/core/stream/adaptation/types.ts +0 -199
- package/src/core/stream/adaptation/utils/create_representation_estimator.ts +0 -114
- package/src/core/stream/index.ts +0 -38
- package/src/core/stream/orchestrator/README.md +0 -349
- package/src/core/stream/orchestrator/get_time_ranges_for_content.ts +0 -70
- package/src/core/stream/orchestrator/index.ts +0 -30
- package/src/core/stream/orchestrator/stream_orchestrator.ts +0 -664
- package/src/core/stream/period/index.ts +0 -20
- package/src/core/stream/period/period_stream.ts +0 -469
- package/src/core/stream/period/types.ts +0 -132
- package/src/core/stream/period/utils/get_adaptation_switch_strategy.ts +0 -287
- package/src/core/stream/representation/README.md +0 -16
- package/src/core/stream/representation/index.ts +0 -20
- package/src/core/stream/representation/representation_stream.ts +0 -474
- package/src/core/stream/representation/types.ts +0 -292
- package/src/core/stream/representation/utils/append_segment_to_buffer.ts +0 -77
- package/src/core/stream/representation/utils/check_for_discontinuity.ts +0 -305
- package/src/core/stream/representation/utils/downloading_queue.ts +0 -603
- package/src/core/stream/representation/utils/force_garbage_collection.ts +0 -113
- package/src/core/stream/representation/utils/get_buffer_status.ts +0 -322
- package/src/core/stream/representation/utils/get_needed_segments.ts +0 -617
- package/src/core/stream/representation/utils/get_segment_priority.ts +0 -43
- package/src/core/stream/representation/utils/push_init_segment.ts +0 -85
- package/src/core/stream/representation/utils/push_media_segment.ts +0 -113
- package/src/default_config.ts +0 -1293
- package/src/errors/README.md +0 -6
- package/src/errors/__tests__/assertion_error.test.ts +0 -26
- package/src/errors/__tests__/encrypted_media_error.test.ts +0 -45
- package/src/errors/__tests__/error_message.test.ts +0 -23
- package/src/errors/__tests__/format_error.test.ts +0 -62
- package/src/errors/__tests__/is_known_error.test.ts +0 -65
- package/src/errors/__tests__/media_error.test.ts +0 -55
- package/src/errors/__tests__/network_error.test.ts +0 -84
- package/src/errors/__tests__/other_error.test.ts +0 -53
- package/src/errors/__tests__/request_error.test.ts +0 -45
- package/src/errors/assertion_error.ts +0 -40
- package/src/errors/custom_loader_error.ts +0 -57
- package/src/errors/encrypted_media_error.ts +0 -71
- package/src/errors/error_codes.ts +0 -149
- package/src/errors/error_message.ts +0 -30
- package/src/errors/format_error.ts +0 -39
- package/src/errors/index.ts +0 -52
- package/src/errors/is_known_error.ts +0 -35
- package/src/errors/media_error.ts +0 -118
- package/src/errors/network_error.ts +0 -74
- package/src/errors/other_error.ts +0 -50
- package/src/errors/request_error.ts +0 -76
- package/src/experimental/README.md +0 -16
- package/src/experimental/features/__tests__/dash_wasm.test.ts +0 -44
- package/src/experimental/features/__tests__/debug_element.test.ts +0 -12
- package/src/experimental/features/__tests__/index.test.ts +0 -19
- package/src/experimental/features/__tests__/local.test.ts +0 -35
- package/src/experimental/features/__tests__/metaplaylist.test.ts +0 -35
- package/src/experimental/features/dash_wasm.ts +0 -41
- package/src/experimental/features/debug_element.ts +0 -13
- package/src/experimental/features/index.ts +0 -20
- package/src/experimental/features/local.ts +0 -28
- package/src/experimental/features/metaplaylist.ts +0 -28
- package/src/experimental/index.ts +0 -5
- package/src/experimental/tools/VideoThumbnailLoader/features/dash.ts +0 -23
- package/src/experimental/tools/VideoThumbnailLoader/features/metaplaylist.ts +0 -23
- package/src/experimental/tools/VideoThumbnailLoader/index.ts +0 -25
- package/src/experimental/tools/VideoThumbnailLoader/load_and_push_segment.ts +0 -77
- package/src/experimental/tools/VideoThumbnailLoader/prepare_source_buffer.ts +0 -75
- package/src/experimental/tools/VideoThumbnailLoader/remove_buffer_around_time.ts +0 -54
- package/src/experimental/tools/VideoThumbnailLoader/types.ts +0 -39
- package/src/experimental/tools/VideoThumbnailLoader/video_thumbnail_loader.ts +0 -423
- package/src/experimental/tools/VideoThumbnailLoader/video_thumbnail_loader_error.ts +0 -34
- package/src/experimental/tools/createMetaplaylist/get_duration_from_manifest.ts +0 -141
- package/src/experimental/tools/createMetaplaylist/index.ts +0 -72
- package/src/experimental/tools/index.ts +0 -27
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/capabilities.test.ts +0 -37
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/probers/DRMInfos.test.ts +0 -140
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/probers/HDCPPolicy.test.ts +0 -153
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/probers/decodingInfos.test.ts +0 -405
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/probers/defaultCodecFinder.test.ts +0 -136
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/probers/mediaContentType.test.ts +0 -294
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/probers/mediaDisplayInfos.test.ts +0 -189
- package/src/experimental/tools/mediaCapabilitiesProber/__tests__/utils.test.ts +0 -361
- package/src/experimental/tools/mediaCapabilitiesProber/api/index.ts +0 -184
- package/src/experimental/tools/mediaCapabilitiesProber/api/probeMediaConfiguration.ts +0 -136
- package/src/experimental/tools/mediaCapabilitiesProber/capabilities.ts +0 -169
- package/src/experimental/tools/mediaCapabilitiesProber/index.ts +0 -18
- package/src/experimental/tools/mediaCapabilitiesProber/log.ts +0 -21
- package/src/experimental/tools/mediaCapabilitiesProber/probers/DRMInfos.ts +0 -67
- package/src/experimental/tools/mediaCapabilitiesProber/probers/HDCPPolicy.ts +0 -89
- package/src/experimental/tools/mediaCapabilitiesProber/probers/decodingInfo.ts +0 -100
- package/src/experimental/tools/mediaCapabilitiesProber/probers/defaultCodecsFinder.ts +0 -66
- package/src/experimental/tools/mediaCapabilitiesProber/probers/index.ts +0 -44
- package/src/experimental/tools/mediaCapabilitiesProber/probers/mediaContentType.ts +0 -66
- package/src/experimental/tools/mediaCapabilitiesProber/probers/mediaContentTypeWithFeatures/format.ts +0 -100
- package/src/experimental/tools/mediaCapabilitiesProber/probers/mediaContentTypeWithFeatures/index.ts +0 -105
- package/src/experimental/tools/mediaCapabilitiesProber/probers/mediaDisplayInfos.ts +0 -54
- package/src/experimental/tools/mediaCapabilitiesProber/types.ts +0 -75
- package/src/experimental/tools/mediaCapabilitiesProber/utils.ts +0 -107
- package/src/experimental/tools/parseBIFThumbnails.ts +0 -39
- package/src/features/README.md +0 -11
- package/src/features/__tests__/add_features.test.ts +0 -69
- package/src/features/__tests__/initialize_features.test.ts +0 -674
- package/src/features/add_features.ts +0 -37
- package/src/features/features_object.ts +0 -37
- package/src/features/index.ts +0 -40
- package/src/features/initialize_features.ts +0 -136
- package/src/features/list/__tests__/bif_parser.test.ts +0 -30
- package/src/features/list/__tests__/dash.test.ts +0 -41
- package/src/features/list/__tests__/directfile.test.ts +0 -35
- package/src/features/list/__tests__/eme.test.ts +0 -28
- package/src/features/list/__tests__/html_sami_parser.test.ts +0 -33
- package/src/features/list/__tests__/html_srt_parser.test.ts +0 -33
- package/src/features/list/__tests__/html_text_buffer.test.ts +0 -29
- package/src/features/list/__tests__/html_ttml_parser.test.ts +0 -33
- package/src/features/list/__tests__/html_vtt_parser.test.ts +0 -33
- package/src/features/list/__tests__/image_buffer.test.ts +0 -28
- package/src/features/list/__tests__/index.test.ts +0 -55
- package/src/features/list/__tests__/native_sami_parser.test.ts +0 -33
- package/src/features/list/__tests__/native_srt_parser.test.ts +0 -33
- package/src/features/list/__tests__/native_text_buffer.test.ts +0 -29
- package/src/features/list/__tests__/native_ttml_parser.test.ts +0 -33
- package/src/features/list/__tests__/native_vtt_parser.test.ts +0 -33
- package/src/features/list/__tests__/smooth.test.ts +0 -36
- package/src/features/list/bif_parser.ts +0 -31
- package/src/features/list/dash.ts +0 -36
- package/src/features/list/directfile.ts +0 -35
- package/src/features/list/eme.ts +0 -29
- package/src/features/list/html_sami_parser.ts +0 -31
- package/src/features/list/html_srt_parser.ts +0 -31
- package/src/features/list/html_text_buffer.ts +0 -29
- package/src/features/list/html_ttml_parser.ts +0 -31
- package/src/features/list/html_vtt_parser.ts +0 -31
- package/src/features/list/image_buffer.ts +0 -29
- package/src/features/list/index.ts +0 -32
- package/src/features/list/native_sami_parser.ts +0 -32
- package/src/features/list/native_srt_parser.ts +0 -32
- package/src/features/list/native_text_buffer.ts +0 -30
- package/src/features/list/native_ttml_parser.ts +0 -32
- package/src/features/list/native_vtt_parser.ts +0 -32
- package/src/features/list/smooth.ts +0 -32
- package/src/features/types.ts +0 -183
- package/src/index.ts +0 -38
- package/src/log.ts +0 -22
- package/src/manifest/README.md +0 -55
- package/src/manifest/__tests__/adaptation.test.ts +0 -485
- package/src/manifest/__tests__/manifest.test.ts +0 -428
- package/src/manifest/__tests__/period.test.ts +0 -769
- package/src/manifest/__tests__/representation.test.ts +0 -297
- package/src/manifest/__tests__/update_period_in_place.test.ts +0 -1074
- package/src/manifest/__tests__/update_periods.test.ts +0 -845
- package/src/manifest/adaptation.ts +0 -294
- package/src/manifest/index.ts +0 -67
- package/src/manifest/manifest.ts +0 -811
- package/src/manifest/period.ts +0 -211
- package/src/manifest/representation.ts +0 -451
- package/src/manifest/representation_index/__tests__/static.test.ts +0 -74
- package/src/manifest/representation_index/index.ts +0 -31
- package/src/manifest/representation_index/static.ts +0 -158
- package/src/manifest/representation_index/types.ts +0 -433
- package/src/manifest/types.ts +0 -33
- package/src/manifest/update_period_in_place.ts +0 -142
- package/src/manifest/update_periods.ts +0 -201
- package/src/manifest/utils.ts +0 -60
- package/src/minimal.ts +0 -34
- package/src/parsers/README.md +0 -12
- package/src/parsers/containers/isobmff/constants.ts +0 -24
- package/src/parsers/containers/isobmff/create_box.ts +0 -81
- package/src/parsers/containers/isobmff/drm/index.ts +0 -17
- package/src/parsers/containers/isobmff/drm/playready.ts +0 -45
- package/src/parsers/containers/isobmff/get_box.ts +0 -278
- package/src/parsers/containers/isobmff/index.ts +0 -51
- package/src/parsers/containers/isobmff/read.ts +0 -105
- package/src/parsers/containers/isobmff/take_pssh_out.ts +0 -101
- package/src/parsers/containers/isobmff/utils.ts +0 -555
- package/src/parsers/containers/matroska/index.ts +0 -21
- package/src/parsers/containers/matroska/utils.ts +0 -313
- package/src/parsers/images/bif.ts +0 -128
- package/src/parsers/manifest/dash/common/__tests__/attach_trickmode_track.test.ts +0 -65
- package/src/parsers/manifest/dash/common/__tests__/convert_supplemental_codecs.test.ts +0 -37
- package/src/parsers/manifest/dash/common/__tests__/flatten_overlapping_period.test.ts +0 -162
- package/src/parsers/manifest/dash/common/__tests__/get_clock_offset.test.ts +0 -65
- package/src/parsers/manifest/dash/common/__tests__/get_http_utc-timing_url.test.ts +0 -165
- package/src/parsers/manifest/dash/common/__tests__/get_periods_time_infos.test.ts +0 -118
- package/src/parsers/manifest/dash/common/__tests__/manifest_bounds_calculator.test.ts +0 -290
- package/src/parsers/manifest/dash/common/__tests__/parse_availability_start_time.test.ts +0 -63
- package/src/parsers/manifest/dash/common/attach_trickmode_track.ts +0 -55
- package/src/parsers/manifest/dash/common/convert_supplemental_codecs.ts +0 -32
- package/src/parsers/manifest/dash/common/flatten_overlapping_periods.ts +0 -87
- package/src/parsers/manifest/dash/common/get_clock_offset.ts +0 -41
- package/src/parsers/manifest/dash/common/get_hdr_information.ts +0 -94
- package/src/parsers/manifest/dash/common/get_http_utc-timing_url.ts +0 -46
- package/src/parsers/manifest/dash/common/get_minimum_and_maximum_positions.ts +0 -39
- package/src/parsers/manifest/dash/common/get_periods_time_infos.ts +0 -91
- package/src/parsers/manifest/dash/common/index.ts +0 -40
- package/src/parsers/manifest/dash/common/indexes/__tests__/tokens.test.ts +0 -60
- package/src/parsers/manifest/dash/common/indexes/base.ts +0 -444
- package/src/parsers/manifest/dash/common/indexes/get_init_segment.ts +0 -55
- package/src/parsers/manifest/dash/common/indexes/get_segments_from_timeline.ts +0 -148
- package/src/parsers/manifest/dash/common/indexes/index.ts +0 -39
- package/src/parsers/manifest/dash/common/indexes/list.ts +0 -338
- package/src/parsers/manifest/dash/common/indexes/template.ts +0 -652
- package/src/parsers/manifest/dash/common/indexes/timeline/__tests__/parse_s_element.test.ts +0 -115
- package/src/parsers/manifest/dash/common/indexes/timeline/construct_timeline_from_elements.ts +0 -54
- package/src/parsers/manifest/dash/common/indexes/timeline/construct_timeline_from_previous_timeline.ts +0 -102
- package/src/parsers/manifest/dash/common/indexes/timeline/convert_element_to_index_segment.ts +0 -66
- package/src/parsers/manifest/dash/common/indexes/timeline/find_first_common_start_time.ts +0 -153
- package/src/parsers/manifest/dash/common/indexes/timeline/index.ts +0 -21
- package/src/parsers/manifest/dash/common/indexes/timeline/parse_s_element.ts +0 -72
- package/src/parsers/manifest/dash/common/indexes/timeline/timeline_representation_index.ts +0 -1049
- package/src/parsers/manifest/dash/common/indexes/tokens.ts +0 -127
- package/src/parsers/manifest/dash/common/indexes/utils.ts +0 -32
- package/src/parsers/manifest/dash/common/infer_adaptation_type.ts +0 -142
- package/src/parsers/manifest/dash/common/manifest_bounds_calculator.ts +0 -165
- package/src/parsers/manifest/dash/common/parse_adaptation_sets.ts +0 -569
- package/src/parsers/manifest/dash/common/parse_availability_start_time.ts +0 -35
- package/src/parsers/manifest/dash/common/parse_mpd.ts +0 -399
- package/src/parsers/manifest/dash/common/parse_periods.ts +0 -363
- package/src/parsers/manifest/dash/common/parse_representation_index.ts +0 -199
- package/src/parsers/manifest/dash/common/parse_representations.ts +0 -352
- package/src/parsers/manifest/dash/common/resolve_base_urls.ts +0 -58
- package/src/parsers/manifest/dash/index.ts +0 -22
- package/src/parsers/manifest/dash/js-parser/__tests__/parse_from_document.test.ts +0 -45
- package/src/parsers/manifest/dash/js-parser/index.ts +0 -18
- package/src/parsers/manifest/dash/js-parser/node_parsers/AdaptationSet.ts +0 -381
- package/src/parsers/manifest/dash/js-parser/node_parsers/BaseURL.ts +0 -35
- package/src/parsers/manifest/dash/js-parser/node_parsers/ContentComponent.ts +0 -49
- package/src/parsers/manifest/dash/js-parser/node_parsers/ContentProtection.ts +0 -94
- package/src/parsers/manifest/dash/js-parser/node_parsers/EventStream.ts +0 -117
- package/src/parsers/manifest/dash/js-parser/node_parsers/Initialization.ts +0 -48
- package/src/parsers/manifest/dash/js-parser/node_parsers/MPD.ts +0 -180
- package/src/parsers/manifest/dash/js-parser/node_parsers/Period.ts +0 -152
- package/src/parsers/manifest/dash/js-parser/node_parsers/Representation.ts +0 -234
- package/src/parsers/manifest/dash/js-parser/node_parsers/SegmentBase.ts +0 -112
- package/src/parsers/manifest/dash/js-parser/node_parsers/SegmentList.ts +0 -50
- package/src/parsers/manifest/dash/js-parser/node_parsers/SegmentTemplate.ts +0 -98
- package/src/parsers/manifest/dash/js-parser/node_parsers/SegmentTimeline.ts +0 -35
- package/src/parsers/manifest/dash/js-parser/node_parsers/SegmentURL.ts +0 -63
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/AdaptationSet.test.ts +0 -407
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/ContentComponent.test.ts +0 -67
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/ContentProtection.test.ts +0 -223
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/Initialization.test.ts +0 -139
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/SegmentTimeline.test.ts +0 -119
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/SegmentURL.test.ts +0 -205
- package/src/parsers/manifest/dash/js-parser/node_parsers/__tests__/utils.test.ts +0 -218
- package/src/parsers/manifest/dash/js-parser/node_parsers/utils.ts +0 -384
- package/src/parsers/manifest/dash/js-parser/parse_from_document.ts +0 -129
- package/src/parsers/manifest/dash/node_parser_types.ts +0 -431
- package/src/parsers/manifest/dash/parsers_types.ts +0 -91
- package/src/parsers/manifest/dash/wasm-parser/Cargo.lock +0 -25
- package/src/parsers/manifest/dash/wasm-parser/Cargo.toml +0 -16
- package/src/parsers/manifest/dash/wasm-parser/README.md +0 -267
- package/src/parsers/manifest/dash/wasm-parser/index.ts +0 -21
- package/src/parsers/manifest/dash/wasm-parser/rs/errors.rs +0 -28
- package/src/parsers/manifest/dash/wasm-parser/rs/events.rs +0 -373
- package/src/parsers/manifest/dash/wasm-parser/rs/lib.rs +0 -85
- package/src/parsers/manifest/dash/wasm-parser/rs/processor/attributes.rs +0 -414
- package/src/parsers/manifest/dash/wasm-parser/rs/processor/mod.rs +0 -472
- package/src/parsers/manifest/dash/wasm-parser/rs/processor/s_element.rs +0 -72
- package/src/parsers/manifest/dash/wasm-parser/rs/reader.rs +0 -17
- package/src/parsers/manifest/dash/wasm-parser/rs/reportable.rs +0 -147
- package/src/parsers/manifest/dash/wasm-parser/rs/utils.rs +0 -217
- package/src/parsers/manifest/dash/wasm-parser/ts/dash-wasm-parser.ts +0 -477
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/AdaptationSet.ts +0 -343
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/BaseURL.ts +0 -38
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/ContentComponent.ts +0 -53
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/ContentProtection.ts +0 -62
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/EventStream.ts +0 -144
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/MPD.ts +0 -183
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/Period.ts +0 -180
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/Representation.ts +0 -215
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/Scheme.ts +0 -44
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/SegmentBase.ts +0 -115
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/SegmentList.ts +0 -61
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/SegmentTemplate.ts +0 -133
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/SegmentUrl.ts +0 -70
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/XLink.ts +0 -66
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/index.ts +0 -17
- package/src/parsers/manifest/dash/wasm-parser/ts/generators/root.ts +0 -66
- package/src/parsers/manifest/dash/wasm-parser/ts/parsers_stack.ts +0 -80
- package/src/parsers/manifest/dash/wasm-parser/ts/types.ts +0 -298
- package/src/parsers/manifest/dash/wasm-parser/ts/utils.ts +0 -47
- package/src/parsers/manifest/index.ts +0 -17
- package/src/parsers/manifest/local/index.ts +0 -25
- package/src/parsers/manifest/local/parse_local_manifest.ts +0 -164
- package/src/parsers/manifest/local/representation_index.ts +0 -246
- package/src/parsers/manifest/local/types.ts +0 -291
- package/src/parsers/manifest/metaplaylist/index.ts +0 -28
- package/src/parsers/manifest/metaplaylist/metaplaylist_parser.ts +0 -335
- package/src/parsers/manifest/metaplaylist/representation_index.ts +0 -251
- package/src/parsers/manifest/smooth/create_parser.ts +0 -699
- package/src/parsers/manifest/smooth/get_codecs.ts +0 -55
- package/src/parsers/manifest/smooth/index.ts +0 -26
- package/src/parsers/manifest/smooth/parse_C_nodes.ts +0 -69
- package/src/parsers/manifest/smooth/parse_protection_node.ts +0 -72
- package/src/parsers/manifest/smooth/representation_index.ts +0 -704
- package/src/parsers/manifest/smooth/utils/add_segment_infos.ts +0 -77
- package/src/parsers/manifest/smooth/utils/parseBoolean.ts +0 -31
- package/src/parsers/manifest/smooth/utils/reduceChildren.ts +0 -36
- package/src/parsers/manifest/smooth/utils/tokens.ts +0 -46
- package/src/parsers/manifest/types.ts +0 -395
- package/src/parsers/manifest/utils/__tests__/get_first_time_from_adaptations.test.ts +0 -161
- package/src/parsers/manifest/utils/__tests__/get_last_time_from_adaptation.test.ts +0 -161
- package/src/parsers/manifest/utils/__tests__/index_helpers.test.ts +0 -55
- package/src/parsers/manifest/utils/__tests__/update_segment_timeline.test.ts +0 -546
- package/src/parsers/manifest/utils/check_manifest_ids.ts +0 -83
- package/src/parsers/manifest/utils/clear_timeline_from_position.ts +0 -74
- package/src/parsers/manifest/utils/get_first_time_from_adaptation.ts +0 -48
- package/src/parsers/manifest/utils/get_last_time_from_adaptation.ts +0 -50
- package/src/parsers/manifest/utils/get_maximum_positions.ts +0 -87
- package/src/parsers/manifest/utils/get_minimum_position.ts +0 -80
- package/src/parsers/manifest/utils/index_helpers.ts +0 -204
- package/src/parsers/manifest/utils/update_segment_timeline.ts +0 -141
- package/src/parsers/texttracks/index.ts +0 -21
- package/src/parsers/texttracks/sami/html.ts +0 -219
- package/src/parsers/texttracks/sami/native.ts +0 -192
- package/src/parsers/texttracks/srt/__tests__/find_end_of_cue_block.test.ts +0 -99
- package/src/parsers/texttracks/srt/__tests__/get_cue_blocks.test.ts +0 -119
- package/src/parsers/texttracks/srt/__tests__/parse_cue.test.ts +0 -123
- package/src/parsers/texttracks/srt/__tests__/parse_timestamp.test.ts +0 -36
- package/src/parsers/texttracks/srt/find_end_of_cue_block.ts +0 -46
- package/src/parsers/texttracks/srt/get_cue_blocks.ts +0 -49
- package/src/parsers/texttracks/srt/html.ts +0 -182
- package/src/parsers/texttracks/srt/native.ts +0 -74
- package/src/parsers/texttracks/srt/parse_cue.ts +0 -76
- package/src/parsers/texttracks/srt/parse_timestamp.ts +0 -37
- package/src/parsers/texttracks/ttml/__tests__/resolve_styles_inheritance.test.ts +0 -248
- package/src/parsers/texttracks/ttml/get_parameters.ts +0 -106
- package/src/parsers/texttracks/ttml/get_styling.ts +0 -146
- package/src/parsers/texttracks/ttml/get_time_delimiters.ts +0 -49
- package/src/parsers/texttracks/ttml/html/__tests__/__global__/html_ttml_parser.test.test.ts +0 -190
- package/src/parsers/texttracks/ttml/html/__tests__/generate_css_test_outline.test.ts +0 -32
- package/src/parsers/texttracks/ttml/html/__tests__/ttml_color_to_css_color.test.ts +0 -62
- package/src/parsers/texttracks/ttml/html/apply_default_ttml_paragraph_style.ts +0 -67
- package/src/parsers/texttracks/ttml/html/apply_extent.ts +0 -65
- package/src/parsers/texttracks/ttml/html/apply_font_size.ts +0 -62
- package/src/parsers/texttracks/ttml/html/apply_line_height.ts +0 -50
- package/src/parsers/texttracks/ttml/html/apply_origin.ts +0 -64
- package/src/parsers/texttracks/ttml/html/apply_padding.ts +0 -141
- package/src/parsers/texttracks/ttml/html/create_element.ts +0 -549
- package/src/parsers/texttracks/ttml/html/generate_css_test_outline.ts +0 -46
- package/src/parsers/texttracks/ttml/html/index.ts +0 -23
- package/src/parsers/texttracks/ttml/html/parse_cue.ts +0 -65
- package/src/parsers/texttracks/ttml/html/parse_ttml_to_div.ts +0 -58
- package/src/parsers/texttracks/ttml/html/ttml_color_to_css_color.ts +0 -68
- package/src/parsers/texttracks/ttml/native/index.ts +0 -23
- package/src/parsers/texttracks/ttml/native/parse_cue.ts +0 -245
- package/src/parsers/texttracks/ttml/native/parse_ttml_to_vtt.ts +0 -39
- package/src/parsers/texttracks/ttml/parse_ttml.ts +0 -206
- package/src/parsers/texttracks/ttml/regexps.ts +0 -65
- package/src/parsers/texttracks/ttml/resolve_styles_inheritance.ts +0 -84
- package/src/parsers/texttracks/ttml/time_parsing.ts +0 -156
- package/src/parsers/texttracks/ttml/xml_utils.ts +0 -166
- package/src/parsers/texttracks/types.ts +0 -34
- package/src/parsers/texttracks/webvtt/__tests__/get_cue_blocks.test.ts +0 -218
- package/src/parsers/texttracks/webvtt/__tests__/get_style_blocks.test.ts +0 -65
- package/src/parsers/texttracks/webvtt/__tests__/parse_cue_block.test.ts +0 -249
- package/src/parsers/texttracks/webvtt/__tests__/parse_timestamp.test.ts +0 -39
- package/src/parsers/texttracks/webvtt/__tests__/utils.test.ts +0 -401
- package/src/parsers/texttracks/webvtt/get_cue_blocks.ts +0 -51
- package/src/parsers/texttracks/webvtt/get_style_blocks.ts +0 -56
- package/src/parsers/texttracks/webvtt/html/__tests__/convert_payload_to_html.test.ts +0 -106
- package/src/parsers/texttracks/webvtt/html/__tests__/create_default_style_elements.test.ts +0 -44
- package/src/parsers/texttracks/webvtt/html/__tests__/create_style_attribute.test.ts +0 -139
- package/src/parsers/texttracks/webvtt/html/__tests__/create_styled_element.test.ts +0 -140
- package/src/parsers/texttracks/webvtt/html/__tests__/parse_style_block.test.ts +0 -345
- package/src/parsers/texttracks/webvtt/html/__tests__/parse_webvtt_to_div.test.ts +0 -181
- package/src/parsers/texttracks/webvtt/html/__tests__/to_html.test.ts +0 -234
- package/src/parsers/texttracks/webvtt/html/convert_payload_to_html.ts +0 -46
- package/src/parsers/texttracks/webvtt/html/create_default_style_elements.ts +0 -26
- package/src/parsers/texttracks/webvtt/html/create_style_attribute.ts +0 -222
- package/src/parsers/texttracks/webvtt/html/create_styled_element.ts +0 -95
- package/src/parsers/texttracks/webvtt/html/index.ts +0 -25
- package/src/parsers/texttracks/webvtt/html/parse_style_block.ts +0 -76
- package/src/parsers/texttracks/webvtt/html/parse_webvtt_to_div.ts +0 -67
- package/src/parsers/texttracks/webvtt/html/to_html.ts +0 -96
- package/src/parsers/texttracks/webvtt/native/index.ts +0 -23
- package/src/parsers/texttracks/webvtt/native/parse_vtt_to_cues.ts +0 -70
- package/src/parsers/texttracks/webvtt/native/set_settings_on_cue.ts +0 -95
- package/src/parsers/texttracks/webvtt/native/to_native_cue.ts +0 -34
- package/src/parsers/texttracks/webvtt/parse_cue_block.ts +0 -128
- package/src/parsers/texttracks/webvtt/parse_timestamp.ts +0 -40
- package/src/parsers/texttracks/webvtt/utils.ts +0 -135
- package/src/public_types.ts +0 -846
- package/src/tools/README.md +0 -4
- package/src/tools/TextTrackRenderer/index.ts +0 -28
- package/src/tools/TextTrackRenderer/text_track_renderer.ts +0 -107
- package/src/tools/index.ts +0 -20
- package/src/tools/string_utils.ts +0 -24
- package/src/transports/README.md +0 -276
- package/src/transports/dash/add_segment_integrity_checks_to_loader.ts +0 -98
- package/src/transports/dash/construct_segment_url.ts +0 -28
- package/src/transports/dash/extract_complete_chunks.ts +0 -66
- package/src/transports/dash/get_events_out_of_emsgs.ts +0 -105
- package/src/transports/dash/image_pipelines.ts +0 -122
- package/src/transports/dash/index.ts +0 -23
- package/src/transports/dash/init_segment_loader.ts +0 -114
- package/src/transports/dash/low_latency_segment_loader.ts +0 -87
- package/src/transports/dash/manifest_parser.ts +0 -325
- package/src/transports/dash/pipelines.ts +0 -72
- package/src/transports/dash/segment_loader.ts +0 -249
- package/src/transports/dash/segment_parser.ts +0 -194
- package/src/transports/dash/text_loader.ts +0 -120
- package/src/transports/dash/text_parser.ts +0 -234
- package/src/transports/index.ts +0 -17
- package/src/transports/local/index.ts +0 -18
- package/src/transports/local/pipelines.ts +0 -100
- package/src/transports/local/segment_loader.ts +0 -198
- package/src/transports/local/segment_parser.ts +0 -101
- package/src/transports/local/text_parser.ts +0 -185
- package/src/transports/metaplaylist/README.md +0 -94
- package/src/transports/metaplaylist/index.ts +0 -23
- package/src/transports/metaplaylist/manifest_loader.ts +0 -62
- package/src/transports/metaplaylist/pipelines.ts +0 -425
- package/src/transports/smooth/extract_timings_infos.ts +0 -142
- package/src/transports/smooth/index.ts +0 -23
- package/src/transports/smooth/isobmff/__tests__/create_boxes.test.ts +0 -231
- package/src/transports/smooth/isobmff/create_audio_init_segment.ts +0 -84
- package/src/transports/smooth/isobmff/create_boxes.ts +0 -481
- package/src/transports/smooth/isobmff/create_init_segment.ts +0 -100
- package/src/transports/smooth/isobmff/create_traf_box.ts +0 -40
- package/src/transports/smooth/isobmff/create_video_init_segment.ts +0 -78
- package/src/transports/smooth/isobmff/get_aaces_header.ts +0 -62
- package/src/transports/smooth/isobmff/index.ts +0 -32
- package/src/transports/smooth/isobmff/parse_tfrf.ts +0 -57
- package/src/transports/smooth/isobmff/parse_tfxd.ts +0 -38
- package/src/transports/smooth/isobmff/patch_segment.ts +0 -171
- package/src/transports/smooth/pipelines.ts +0 -533
- package/src/transports/smooth/segment_loader.ts +0 -288
- package/src/transports/smooth/utils.ts +0 -106
- package/src/transports/types.ts +0 -809
- package/src/transports/utils/__tests__/byte_range.test.ts +0 -35
- package/src/transports/utils/__tests__/check_isobmff_integrity.test.ts +0 -148
- package/src/transports/utils/__tests__/find_complete_box.test.ts +0 -138
- package/src/transports/utils/__tests__/infer_segment_container.test.ts +0 -227
- package/src/transports/utils/byte_range.ts +0 -25
- package/src/transports/utils/call_custom_manifest_loader.ts +0 -147
- package/src/transports/utils/check_isobmff_integrity.ts +0 -50
- package/src/transports/utils/find_complete_box.ts +0 -63
- package/src/transports/utils/generate_manifest_loader.ts +0 -97
- package/src/transports/utils/get_isobmff_timing_infos.ts +0 -86
- package/src/transports/utils/infer_segment_container.ts +0 -56
- package/src/transports/utils/parse_text_track.ts +0 -176
- package/src/typings/README.md +0 -7
- package/src/typings/globals.d.ts +0 -83
- package/src/typings/next-tick.d.ts +0 -23
- package/src/utils/README.md +0 -5
- package/src/utils/__tests__/are_arrays_of_numbers_equal.test.ts +0 -86
- package/src/utils/__tests__/are_codecs_compatible.test.ts +0 -88
- package/src/utils/__tests__/array_find.test.ts +0 -113
- package/src/utils/__tests__/array_find_index.test.ts +0 -113
- package/src/utils/__tests__/array_includes.test.ts +0 -151
- package/src/utils/__tests__/assert.test.ts +0 -237
- package/src/utils/__tests__/assert_unreachable.test.ts +0 -40
- package/src/utils/__tests__/base64.test.ts +0 -147
- package/src/utils/__tests__/byte_parsing.test.ts +0 -267
- package/src/utils/__tests__/deep_merge.test.ts +0 -48
- package/src/utils/__tests__/event_emitter.test.ts +0 -579
- package/src/utils/__tests__/flat_map.test.ts +0 -71
- package/src/utils/__tests__/get_fuzzed_delay.test.ts +0 -32
- package/src/utils/__tests__/hash_buffer.test.ts +0 -105
- package/src/utils/__tests__/id_generator.test.ts +0 -80
- package/src/utils/__tests__/initialization_segment_cache.test.ts +0 -245
- package/src/utils/__tests__/is_non_empty_string.test.ts +0 -41
- package/src/utils/__tests__/is_null_or_undefined.test.ts +0 -33
- package/src/utils/__tests__/list_to_map.test.ts +0 -46
- package/src/utils/__tests__/logger.test.ts +0 -214
- package/src/utils/__tests__/noop.test.ts +0 -23
- package/src/utils/__tests__/object_assign.test.ts +0 -56
- package/src/utils/__tests__/object_values.test.ts +0 -26
- package/src/utils/__tests__/ranges.test.ts +0 -907
- package/src/utils/__tests__/resolve_url.test.ts +0 -100
- package/src/utils/__tests__/simple_set.test.ts +0 -57
- package/src/utils/__tests__/sorted_list.test.ts +0 -335
- package/src/utils/__tests__/starts_with.test.ts +0 -65
- package/src/utils/__tests__/string_parsing.test.ts +0 -267
- package/src/utils/__tests__/uniq.test.ts +0 -134
- package/src/utils/__tests__/warn_once.test.ts +0 -38
- package/src/utils/__tests__/weak_map_memory.test.ts +0 -188
- package/src/utils/are_arrays_of_numbers_equal.ts +0 -39
- package/src/utils/are_codecs_compatible.ts +0 -51
- package/src/utils/array_find.ts +0 -55
- package/src/utils/array_find_index.ts +0 -54
- package/src/utils/array_includes.ts +0 -93
- package/src/utils/assert.ts +0 -65
- package/src/utils/assert_unreachable.ts +0 -45
- package/src/utils/base64.ts +0 -153
- package/src/utils/byte_parsing.ts +0 -256
- package/src/utils/cancellable_sleep.ts +0 -41
- package/src/utils/create_cancellable_promise.ts +0 -69
- package/src/utils/deep_merge.ts +0 -49
- package/src/utils/event_emitter.ts +0 -147
- package/src/utils/flat_map.ts +0 -50
- package/src/utils/get_fuzzed_delay.ts +0 -27
- package/src/utils/hash_buffer.ts +0 -42
- package/src/utils/id_generator.ts +0 -35
- package/src/utils/initialization_segment_cache.ts +0 -68
- package/src/utils/is_non_empty_string.ts +0 -23
- package/src/utils/is_null_or_undefined.ts +0 -27
- package/src/utils/languages/ISO_639-1_to_ISO_639-3.ts +0 -207
- package/src/utils/languages/ISO_639-2_to_ISO_639-3.ts +0 -43
- package/src/utils/languages/__tests__/normalize.test.ts +0 -290
- package/src/utils/languages/index.ts +0 -29
- package/src/utils/languages/normalize.ts +0 -152
- package/src/utils/list_to_map.ts +0 -32
- package/src/utils/logger.ts +0 -100
- package/src/utils/noop.ts +0 -26
- package/src/utils/object_assign.ts +0 -60
- package/src/utils/object_values.ts +0 -31
- package/src/utils/ranges.ts +0 -499
- package/src/utils/reference.ts +0 -390
- package/src/utils/request/fetch.ts +0 -250
- package/src/utils/request/index.ts +0 -38
- package/src/utils/request/xhr.ts +0 -287
- package/src/utils/resolve_url.ts +0 -126
- package/src/utils/retry_promise_with_backoff.ts +0 -95
- package/src/utils/simple_set.ts +0 -67
- package/src/utils/sleep.ts +0 -14
- package/src/utils/slice_uint8array.ts +0 -53
- package/src/utils/sorted_list.ts +0 -240
- package/src/utils/starts_with.ts +0 -42
- package/src/utils/string_parsing.ts +0 -414
- package/src/utils/task_canceller.ts +0 -367
- package/src/utils/uniq.ts +0 -49
- package/src/utils/warn_once.ts +0 -34
- package/src/utils/weak_map_memory.ts +0 -89
- package/src/utils/wrapInPromise.ts +0 -24
- package/tsconfig.json +0 -28
- package/tsconfig.modules.json +0 -36
|
@@ -1,3247 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Copyright 2015 CANAL+ Group
|
|
3
|
-
*
|
|
4
|
-
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
-
* you may not use this file except in compliance with the License.
|
|
6
|
-
* You may obtain a copy of the License at
|
|
7
|
-
*
|
|
8
|
-
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
-
*
|
|
10
|
-
* Unless required by applicable law or agreed to in writing, software
|
|
11
|
-
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
-
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
-
* See the License for the specific language governing permissions and
|
|
14
|
-
* limitations under the License.
|
|
15
|
-
*/
|
|
16
|
-
|
|
17
|
-
/**
|
|
18
|
-
* This file defines the public API for the RxPlayer.
|
|
19
|
-
* It also starts the different sub-parts of the player on various API calls.
|
|
20
|
-
*/
|
|
21
|
-
|
|
22
|
-
import {
|
|
23
|
-
events,
|
|
24
|
-
exitFullscreen,
|
|
25
|
-
getStartDate,
|
|
26
|
-
isFullscreen,
|
|
27
|
-
requestFullscreen,
|
|
28
|
-
} from "../../compat";
|
|
29
|
-
/* eslint-disable-next-line max-len */
|
|
30
|
-
import canRelyOnVideoVisibilityAndSize from "../../compat/can_rely_on_video_visibility_and_size";
|
|
31
|
-
import config from "../../config";
|
|
32
|
-
import {
|
|
33
|
-
ErrorCodes,
|
|
34
|
-
ErrorTypes,
|
|
35
|
-
formatError,
|
|
36
|
-
IErrorCode,
|
|
37
|
-
IErrorType,
|
|
38
|
-
MediaError,
|
|
39
|
-
} from "../../errors";
|
|
40
|
-
import features, {
|
|
41
|
-
addFeatures,
|
|
42
|
-
IFeature,
|
|
43
|
-
} from "../../features";
|
|
44
|
-
import log from "../../log";
|
|
45
|
-
import Manifest, {
|
|
46
|
-
Adaptation,
|
|
47
|
-
Period,
|
|
48
|
-
Representation,
|
|
49
|
-
} from "../../manifest";
|
|
50
|
-
import {
|
|
51
|
-
IAdaptation,
|
|
52
|
-
IAudioTrack,
|
|
53
|
-
IAudioTrackPreference,
|
|
54
|
-
IAvailableAudioTrack,
|
|
55
|
-
IAvailableTextTrack,
|
|
56
|
-
IAvailableVideoTrack,
|
|
57
|
-
IBifThumbnail,
|
|
58
|
-
IBitrateEstimate,
|
|
59
|
-
IConstructorOptions,
|
|
60
|
-
IDecipherabilityUpdateContent,
|
|
61
|
-
IKeySystemConfigurationOutput,
|
|
62
|
-
IKeySystemOption,
|
|
63
|
-
ILoadVideoOptions,
|
|
64
|
-
IPeriod,
|
|
65
|
-
IPlayerError,
|
|
66
|
-
IPlayerState,
|
|
67
|
-
IPositionUpdate,
|
|
68
|
-
IRepresentation,
|
|
69
|
-
IStreamEvent,
|
|
70
|
-
ITextTrack,
|
|
71
|
-
ITextTrackPreference,
|
|
72
|
-
IVideoTrack,
|
|
73
|
-
IVideoTrackPreference,
|
|
74
|
-
} from "../../public_types";
|
|
75
|
-
import areArraysOfNumbersEqual from "../../utils/are_arrays_of_numbers_equal";
|
|
76
|
-
import arrayIncludes from "../../utils/array_includes";
|
|
77
|
-
import assert from "../../utils/assert";
|
|
78
|
-
import EventEmitter, {
|
|
79
|
-
IEventPayload,
|
|
80
|
-
IListener,
|
|
81
|
-
} from "../../utils/event_emitter";
|
|
82
|
-
import idGenerator from "../../utils/id_generator";
|
|
83
|
-
import isNullOrUndefined from "../../utils/is_null_or_undefined";
|
|
84
|
-
import Logger from "../../utils/logger";
|
|
85
|
-
import objectAssign from "../../utils/object_assign";
|
|
86
|
-
import {
|
|
87
|
-
getLeftSizeOfRange,
|
|
88
|
-
getPlayedSizeOfRange,
|
|
89
|
-
getSizeOfRange,
|
|
90
|
-
} from "../../utils/ranges";
|
|
91
|
-
import SharedReference, {
|
|
92
|
-
createMappedReference,
|
|
93
|
-
IReadOnlySharedReference,
|
|
94
|
-
} from "../../utils/reference";
|
|
95
|
-
import TaskCanceller, {
|
|
96
|
-
CancellationSignal,
|
|
97
|
-
} from "../../utils/task_canceller";
|
|
98
|
-
import warnOnce from "../../utils/warn_once";
|
|
99
|
-
import { IABRThrottlers } from "../adaptive";
|
|
100
|
-
import {
|
|
101
|
-
clearOnStop,
|
|
102
|
-
disposeDecryptionResources,
|
|
103
|
-
getKeySystemConfiguration,
|
|
104
|
-
getCurrentKeySystem,
|
|
105
|
-
} from "../decrypt";
|
|
106
|
-
import { ContentInitializer } from "../init";
|
|
107
|
-
import SegmentBuffersStore, {
|
|
108
|
-
IBufferedChunk,
|
|
109
|
-
IBufferType,
|
|
110
|
-
} from "../segment_buffers";
|
|
111
|
-
import { IInbandEvent } from "../stream";
|
|
112
|
-
import {
|
|
113
|
-
checkReloadOptions,
|
|
114
|
-
IParsedLoadVideoOptions,
|
|
115
|
-
IParsedStartAtOption,
|
|
116
|
-
parseConstructorOptions,
|
|
117
|
-
parseLoadVideoOptions,
|
|
118
|
-
} from "./option_utils";
|
|
119
|
-
import PlaybackObserver, {
|
|
120
|
-
IPlaybackObservation,
|
|
121
|
-
} from "./playback_observer";
|
|
122
|
-
/* eslint-disable-next-line max-len */
|
|
123
|
-
import MediaElementTrackChoiceManager from "./tracks_management/media_element_track_choice_manager";
|
|
124
|
-
import TrackChoiceManager from "./tracks_management/track_choice_manager";
|
|
125
|
-
import {
|
|
126
|
-
constructPlayerStateReference,
|
|
127
|
-
emitPlayPauseEvents,
|
|
128
|
-
emitSeekEvents,
|
|
129
|
-
isLoadedState,
|
|
130
|
-
PLAYER_STATES,
|
|
131
|
-
} from "./utils";
|
|
132
|
-
|
|
133
|
-
/* eslint-disable @typescript-eslint/naming-convention */
|
|
134
|
-
|
|
135
|
-
const generateContentId = idGenerator();
|
|
136
|
-
|
|
137
|
-
const { getPageActivityRef,
|
|
138
|
-
getPictureOnPictureStateRef,
|
|
139
|
-
getVideoVisibilityRef,
|
|
140
|
-
getVideoWidthRef,
|
|
141
|
-
onFullscreenChange,
|
|
142
|
-
onTextTrackAdded,
|
|
143
|
-
onTextTrackRemoved } = events;
|
|
144
|
-
|
|
145
|
-
/**
|
|
146
|
-
* @class Player
|
|
147
|
-
* @extends EventEmitter
|
|
148
|
-
*/
|
|
149
|
-
class Player extends EventEmitter<IPublicAPIEvent> {
|
|
150
|
-
|
|
151
|
-
/** Current version of the RxPlayer. */
|
|
152
|
-
public static version : string;
|
|
153
|
-
|
|
154
|
-
/** Current version of the RxPlayer. */
|
|
155
|
-
public readonly version : string;
|
|
156
|
-
|
|
157
|
-
/**
|
|
158
|
-
* Media element attached to the RxPlayer.
|
|
159
|
-
* Set to `null` when the RxPlayer is disposed.
|
|
160
|
-
*/
|
|
161
|
-
public videoElement : HTMLMediaElement|null; // null on dispose
|
|
162
|
-
|
|
163
|
-
/** Logger the RxPlayer uses. */
|
|
164
|
-
public readonly log : Logger;
|
|
165
|
-
|
|
166
|
-
/**
|
|
167
|
-
* Current state of the RxPlayer.
|
|
168
|
-
* Please use `getPlayerState()` instead.
|
|
169
|
-
*/
|
|
170
|
-
public state : IPlayerState;
|
|
171
|
-
|
|
172
|
-
/**
|
|
173
|
-
* Emit when the the RxPlayer is not needed anymore and thus all resources
|
|
174
|
-
* used for its normal functionment can be freed.
|
|
175
|
-
* The player will be unusable after that.
|
|
176
|
-
*/
|
|
177
|
-
private readonly _destroyCanceller : TaskCanceller;
|
|
178
|
-
|
|
179
|
-
/**
|
|
180
|
-
* Contains `true` when the previous content is cleaning-up, `false` when it's
|
|
181
|
-
* done.
|
|
182
|
-
* A new content cannot be launched until it stores `false`.
|
|
183
|
-
*/
|
|
184
|
-
private readonly _priv_contentLock : SharedReference<boolean>;
|
|
185
|
-
|
|
186
|
-
/**
|
|
187
|
-
* The speed that should be applied to playback.
|
|
188
|
-
* Used instead of videoElement.playbackRate to allow more flexibility.
|
|
189
|
-
*/
|
|
190
|
-
private readonly _priv_speed : SharedReference<number>;
|
|
191
|
-
|
|
192
|
-
/** Store buffer-related options used needed when initializing a content. */
|
|
193
|
-
private readonly _priv_bufferOptions : {
|
|
194
|
-
/** Last wanted buffer goal. */
|
|
195
|
-
wantedBufferAhead : SharedReference<number>;
|
|
196
|
-
/** Maximum kept buffer ahead in the current position, in seconds. */
|
|
197
|
-
maxBufferAhead : SharedReference<number>;
|
|
198
|
-
/** Maximum kept buffer behind in the current position, in seconds. */
|
|
199
|
-
maxBufferBehind : SharedReference<number>;
|
|
200
|
-
/** Maximum size of video buffer , in kiloBytes */
|
|
201
|
-
maxVideoBufferSize : SharedReference<number>;
|
|
202
|
-
};
|
|
203
|
-
|
|
204
|
-
/** Information on the current bitrate settings. */
|
|
205
|
-
private readonly _priv_bitrateInfos : {
|
|
206
|
-
/**
|
|
207
|
-
* Store last bitrates for each media type for the adaptive logic.
|
|
208
|
-
* Store the initial wanted bitrates at first.
|
|
209
|
-
*/
|
|
210
|
-
lastBitrates : { audio? : number;
|
|
211
|
-
video? : number;
|
|
212
|
-
text? : number;
|
|
213
|
-
image? : number; };
|
|
214
|
-
|
|
215
|
-
/** Store last wanted minAutoBitrates for the adaptive logic. */
|
|
216
|
-
minAutoBitrates : { audio : SharedReference<number>;
|
|
217
|
-
video : SharedReference<number>; };
|
|
218
|
-
|
|
219
|
-
/** Store last wanted maxAutoBitrates for the adaptive logic. */
|
|
220
|
-
maxAutoBitrates : { audio : SharedReference<number>;
|
|
221
|
-
video : SharedReference<number>; };
|
|
222
|
-
|
|
223
|
-
/** Store last wanted manual bitrates for the adaptive logic. */
|
|
224
|
-
manualBitrates : { audio : SharedReference<number>;
|
|
225
|
-
video : SharedReference<number>; };
|
|
226
|
-
};
|
|
227
|
-
|
|
228
|
-
/**
|
|
229
|
-
* Current fatal error which STOPPED the player.
|
|
230
|
-
* `null` if no fatal error was received for the current or last content.
|
|
231
|
-
*/
|
|
232
|
-
private _priv_currentError : Error|null;
|
|
233
|
-
|
|
234
|
-
/**
|
|
235
|
-
* Information about the current content being played.
|
|
236
|
-
* `null` when no content is currently loading or loaded.
|
|
237
|
-
*/
|
|
238
|
-
private _priv_contentInfos : IPublicApiContentInfos | null;
|
|
239
|
-
|
|
240
|
-
/** List of favorite audio tracks, in preference order. */
|
|
241
|
-
private _priv_preferredAudioTracks : IAudioTrackPreference[];
|
|
242
|
-
|
|
243
|
-
/** List of favorite text tracks, in preference order. */
|
|
244
|
-
private _priv_preferredTextTracks : ITextTrackPreference[];
|
|
245
|
-
|
|
246
|
-
/** List of favorite video tracks, in preference order. */
|
|
247
|
-
private _priv_preferredVideoTracks : IVideoTrackPreference[];
|
|
248
|
-
|
|
249
|
-
/** If `true` trickMode video tracks will be chosen if available. */
|
|
250
|
-
private _priv_preferTrickModeTracks : boolean;
|
|
251
|
-
|
|
252
|
-
/** Refer to last picture in picture event received. */
|
|
253
|
-
private _priv_pictureInPictureRef : IReadOnlySharedReference<
|
|
254
|
-
events.IPictureInPictureEvent
|
|
255
|
-
>;
|
|
256
|
-
|
|
257
|
-
/** Store wanted configuration for the `limitVideoWidth` option. */
|
|
258
|
-
private readonly _priv_limitVideoWidth : boolean;
|
|
259
|
-
|
|
260
|
-
/** Store wanted configuration for the `throttleWhenHidden` option. */
|
|
261
|
-
private readonly _priv_throttleWhenHidden : boolean;
|
|
262
|
-
|
|
263
|
-
/** Store wanted configuration for the `throttleVideoBitrateWhenHidden` option. */
|
|
264
|
-
private readonly _priv_throttleVideoBitrateWhenHidden : boolean;
|
|
265
|
-
|
|
266
|
-
/** Store volume when mute is called, to restore it on unmute. */
|
|
267
|
-
private _priv_mutedMemory : number;
|
|
268
|
-
|
|
269
|
-
/**
|
|
270
|
-
* Store last state of various values sent as events, to avoid re-triggering
|
|
271
|
-
* them multiple times in a row.
|
|
272
|
-
*
|
|
273
|
-
* All those events are linked to the content being played and can be cleaned
|
|
274
|
-
* on stop.
|
|
275
|
-
*/
|
|
276
|
-
private _priv_contentEventsMemory : {
|
|
277
|
-
[P in keyof IPublicAPIEvent]? : IPublicAPIEvent[P];
|
|
278
|
-
};
|
|
279
|
-
|
|
280
|
-
/** Determines whether or not the player should stop at the end of video playback. */
|
|
281
|
-
private readonly _priv_stopAtEnd : boolean;
|
|
282
|
-
|
|
283
|
-
/**
|
|
284
|
-
* Information that can be relied on once `reload` is called.
|
|
285
|
-
* It should refer to the last content being played.
|
|
286
|
-
*/
|
|
287
|
-
private _priv_reloadingMetadata : {
|
|
288
|
-
/**
|
|
289
|
-
* `loadVideo` options communicated for the last content that will be re-used
|
|
290
|
-
* on reload.
|
|
291
|
-
*/
|
|
292
|
-
options?: IParsedLoadVideoOptions;
|
|
293
|
-
/**
|
|
294
|
-
* Manifest loaded for the last content that should be used once `reload`
|
|
295
|
-
* is called.
|
|
296
|
-
*/
|
|
297
|
-
manifest?: Manifest;
|
|
298
|
-
/**
|
|
299
|
-
* If `true`, the player should be paused after reloading.
|
|
300
|
-
* If `false`, the player should be playing after reloading.
|
|
301
|
-
* If `undefined`, `reload` should depend on other criteria (such as the
|
|
302
|
-
* `autoPlay` option, to know whether the content should play or not after
|
|
303
|
-
* reloading.
|
|
304
|
-
*/
|
|
305
|
-
reloadInPause?: boolean;
|
|
306
|
-
/**
|
|
307
|
-
* If set this is the position that should be seeked to by default after
|
|
308
|
-
* reloading.
|
|
309
|
-
*/
|
|
310
|
-
reloadPosition?: number;
|
|
311
|
-
};
|
|
312
|
-
|
|
313
|
-
/**
|
|
314
|
-
* Store last value of autoPlay, from the last load or reload.
|
|
315
|
-
*/
|
|
316
|
-
private _priv_lastAutoPlay: boolean;
|
|
317
|
-
|
|
318
|
-
/** All possible Error types emitted by the RxPlayer. */
|
|
319
|
-
static get ErrorTypes() : Record<IErrorType, IErrorType> {
|
|
320
|
-
return ErrorTypes;
|
|
321
|
-
}
|
|
322
|
-
|
|
323
|
-
/** All possible Error codes emitted by the RxPlayer. */
|
|
324
|
-
static get ErrorCodes() : Record<IErrorCode, IErrorCode> {
|
|
325
|
-
return ErrorCodes;
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
/**
|
|
329
|
-
* Current log level.
|
|
330
|
-
* Update current log level.
|
|
331
|
-
* Should be either (by verbosity ascending):
|
|
332
|
-
* - "NONE"
|
|
333
|
-
* - "ERROR"
|
|
334
|
-
* - "WARNING"
|
|
335
|
-
* - "INFO"
|
|
336
|
-
* - "DEBUG"
|
|
337
|
-
* Any other value will be translated to "NONE".
|
|
338
|
-
*/
|
|
339
|
-
static get LogLevel() : string {
|
|
340
|
-
return log.getLevel();
|
|
341
|
-
}
|
|
342
|
-
static set LogLevel(logLevel : string) {
|
|
343
|
-
log.setLevel(logLevel);
|
|
344
|
-
}
|
|
345
|
-
|
|
346
|
-
/**
|
|
347
|
-
* Add feature(s) to the RxPlayer.
|
|
348
|
-
* @param {Array.<Object>} featureList - Features wanted.
|
|
349
|
-
*/
|
|
350
|
-
static addFeatures(featureList : IFeature[]) : void {
|
|
351
|
-
addFeatures(featureList);
|
|
352
|
-
}
|
|
353
|
-
|
|
354
|
-
/**
|
|
355
|
-
* @constructor
|
|
356
|
-
* @param {Object} options
|
|
357
|
-
*/
|
|
358
|
-
constructor(options : IConstructorOptions = {}) {
|
|
359
|
-
super();
|
|
360
|
-
const { initialAudioBitrate,
|
|
361
|
-
initialVideoBitrate,
|
|
362
|
-
limitVideoWidth,
|
|
363
|
-
minAudioBitrate,
|
|
364
|
-
minVideoBitrate,
|
|
365
|
-
maxAudioBitrate,
|
|
366
|
-
maxBufferAhead,
|
|
367
|
-
maxBufferBehind,
|
|
368
|
-
maxVideoBitrate,
|
|
369
|
-
preferredAudioTracks,
|
|
370
|
-
preferredTextTracks,
|
|
371
|
-
preferredVideoTracks,
|
|
372
|
-
throttleWhenHidden,
|
|
373
|
-
throttleVideoBitrateWhenHidden,
|
|
374
|
-
videoElement,
|
|
375
|
-
wantedBufferAhead,
|
|
376
|
-
maxVideoBufferSize,
|
|
377
|
-
stopAtEnd } = parseConstructorOptions(options);
|
|
378
|
-
const { DEFAULT_UNMUTED_VOLUME } = config.getCurrent();
|
|
379
|
-
// Workaround to support Firefox autoplay on FF 42.
|
|
380
|
-
// See: https://bugzilla.mozilla.org/show_bug.cgi?id=1194624
|
|
381
|
-
videoElement.preload = "auto";
|
|
382
|
-
|
|
383
|
-
this.version = /* PLAYER_VERSION */"3.33.0";
|
|
384
|
-
this.log = log;
|
|
385
|
-
this.state = "STOPPED";
|
|
386
|
-
this.videoElement = videoElement;
|
|
387
|
-
|
|
388
|
-
const destroyCanceller = new TaskCanceller();
|
|
389
|
-
this._destroyCanceller = destroyCanceller;
|
|
390
|
-
|
|
391
|
-
this._priv_pictureInPictureRef = getPictureOnPictureStateRef(videoElement,
|
|
392
|
-
destroyCanceller.signal);
|
|
393
|
-
|
|
394
|
-
/** @deprecated */
|
|
395
|
-
onFullscreenChange(videoElement, () => {
|
|
396
|
-
/* eslint-disable import/no-deprecated */
|
|
397
|
-
this.trigger("fullscreenChange", this.isFullscreen());
|
|
398
|
-
/* eslint-enable import/no-deprecated */
|
|
399
|
-
}, destroyCanceller.signal);
|
|
400
|
-
|
|
401
|
-
/** Store last known TextTrack array linked to the media element. */
|
|
402
|
-
let prevTextTracks : TextTrack[] = [] ;
|
|
403
|
-
for (let i = 0; i < videoElement.textTracks?.length; i++) {
|
|
404
|
-
const textTrack = videoElement.textTracks?.[i];
|
|
405
|
-
if (!isNullOrUndefined(textTrack)) {
|
|
406
|
-
prevTextTracks.push(textTrack);
|
|
407
|
-
}
|
|
408
|
-
}
|
|
409
|
-
|
|
410
|
-
/** Callback called when a TextTrack element is added or removed. */
|
|
411
|
-
const onTextTrackChanges = (_evt : unknown) => {
|
|
412
|
-
const evt = _evt as Event;
|
|
413
|
-
const target = evt.target as TextTrackList;
|
|
414
|
-
const textTrackArr : TextTrack[] = [];
|
|
415
|
-
for (let i = 0; i < target.length; i++) {
|
|
416
|
-
const textTrack = target[i];
|
|
417
|
-
textTrackArr.push(textTrack);
|
|
418
|
-
}
|
|
419
|
-
|
|
420
|
-
const oldTextTracks = prevTextTracks;
|
|
421
|
-
prevTextTracks = textTrackArr;
|
|
422
|
-
|
|
423
|
-
// We can have two consecutive textTrackChanges with the exact same
|
|
424
|
-
// payload when we perform multiple texttrack operations before the event
|
|
425
|
-
// loop is freed.
|
|
426
|
-
if (oldTextTracks.length !== textTrackArr.length) {
|
|
427
|
-
this._priv_onNativeTextTracksNext(textTrackArr);
|
|
428
|
-
return;
|
|
429
|
-
}
|
|
430
|
-
for (let i = 0; i < oldTextTracks.length; i++) {
|
|
431
|
-
if (oldTextTracks[i] !== textTrackArr[i]) {
|
|
432
|
-
this._priv_onNativeTextTracksNext(textTrackArr);
|
|
433
|
-
return ;
|
|
434
|
-
}
|
|
435
|
-
}
|
|
436
|
-
return ;
|
|
437
|
-
};
|
|
438
|
-
|
|
439
|
-
if (!isNullOrUndefined(videoElement.textTracks)) {
|
|
440
|
-
onTextTrackAdded(videoElement.textTracks,
|
|
441
|
-
onTextTrackChanges,
|
|
442
|
-
destroyCanceller.signal);
|
|
443
|
-
onTextTrackRemoved(videoElement.textTracks,
|
|
444
|
-
onTextTrackChanges,
|
|
445
|
-
destroyCanceller.signal);
|
|
446
|
-
}
|
|
447
|
-
|
|
448
|
-
this._priv_speed = new SharedReference(videoElement.playbackRate,
|
|
449
|
-
this._destroyCanceller.signal);
|
|
450
|
-
this._priv_preferTrickModeTracks = false;
|
|
451
|
-
this._priv_contentLock = new SharedReference<boolean>(
|
|
452
|
-
false,
|
|
453
|
-
this._destroyCanceller.signal);
|
|
454
|
-
|
|
455
|
-
this._priv_bufferOptions = {
|
|
456
|
-
wantedBufferAhead: new SharedReference(wantedBufferAhead,
|
|
457
|
-
this._destroyCanceller.signal),
|
|
458
|
-
maxBufferAhead: new SharedReference(maxBufferAhead,
|
|
459
|
-
this._destroyCanceller.signal),
|
|
460
|
-
maxBufferBehind: new SharedReference(maxBufferBehind,
|
|
461
|
-
this._destroyCanceller.signal),
|
|
462
|
-
maxVideoBufferSize: new SharedReference(maxVideoBufferSize,
|
|
463
|
-
this._destroyCanceller.signal),
|
|
464
|
-
};
|
|
465
|
-
|
|
466
|
-
this._priv_bitrateInfos = {
|
|
467
|
-
lastBitrates: { audio: initialAudioBitrate,
|
|
468
|
-
video: initialVideoBitrate },
|
|
469
|
-
minAutoBitrates: { audio: new SharedReference(minAudioBitrate,
|
|
470
|
-
this._destroyCanceller.signal),
|
|
471
|
-
video: new SharedReference(minVideoBitrate,
|
|
472
|
-
this._destroyCanceller.signal) },
|
|
473
|
-
maxAutoBitrates: { audio: new SharedReference(maxAudioBitrate,
|
|
474
|
-
this._destroyCanceller.signal),
|
|
475
|
-
video: new SharedReference(maxVideoBitrate,
|
|
476
|
-
this._destroyCanceller.signal) },
|
|
477
|
-
manualBitrates: { audio: new SharedReference(-1, this._destroyCanceller.signal),
|
|
478
|
-
video: new SharedReference(-1, this._destroyCanceller.signal) },
|
|
479
|
-
};
|
|
480
|
-
|
|
481
|
-
this._priv_throttleWhenHidden = throttleWhenHidden;
|
|
482
|
-
this._priv_throttleVideoBitrateWhenHidden = throttleVideoBitrateWhenHidden;
|
|
483
|
-
this._priv_limitVideoWidth = limitVideoWidth;
|
|
484
|
-
this._priv_mutedMemory = DEFAULT_UNMUTED_VOLUME;
|
|
485
|
-
|
|
486
|
-
this._priv_currentError = null;
|
|
487
|
-
this._priv_contentInfos = null;
|
|
488
|
-
|
|
489
|
-
this._priv_contentEventsMemory = {};
|
|
490
|
-
|
|
491
|
-
this._priv_stopAtEnd = stopAtEnd;
|
|
492
|
-
|
|
493
|
-
this._priv_setPlayerState(PLAYER_STATES.STOPPED);
|
|
494
|
-
|
|
495
|
-
this._priv_preferredAudioTracks = preferredAudioTracks;
|
|
496
|
-
this._priv_preferredTextTracks = preferredTextTracks;
|
|
497
|
-
this._priv_preferredVideoTracks = preferredVideoTracks;
|
|
498
|
-
|
|
499
|
-
this._priv_reloadingMetadata = {};
|
|
500
|
-
|
|
501
|
-
this._priv_lastAutoPlay = false;
|
|
502
|
-
}
|
|
503
|
-
|
|
504
|
-
/**
|
|
505
|
-
* Register a new callback for a player event event.
|
|
506
|
-
*
|
|
507
|
-
* @param {string} evt - The event to register a callback to
|
|
508
|
-
* @param {Function} fn - The callback to call as that event is triggered.
|
|
509
|
-
* The callback will take as argument the eventual payload of the event
|
|
510
|
-
* (single argument).
|
|
511
|
-
*/
|
|
512
|
-
addEventListener<TEventName extends keyof IPublicAPIEvent>(
|
|
513
|
-
evt: TEventName,
|
|
514
|
-
fn: IListener<IPublicAPIEvent, TEventName>
|
|
515
|
-
) : void {
|
|
516
|
-
// The EventEmitter's `addEventListener` method takes an optional third
|
|
517
|
-
// argument that we do not want to expose in the public API.
|
|
518
|
-
// We thus overwrite that function to remove any possible usage of that
|
|
519
|
-
// third argument.
|
|
520
|
-
return super.addEventListener(evt, fn);
|
|
521
|
-
}
|
|
522
|
-
|
|
523
|
-
/**
|
|
524
|
-
* Stop the playback for the current content.
|
|
525
|
-
*/
|
|
526
|
-
stop() : void {
|
|
527
|
-
if (this._priv_contentInfos !== null) {
|
|
528
|
-
this._priv_contentInfos.currentContentCanceller.cancel();
|
|
529
|
-
}
|
|
530
|
-
this._priv_cleanUpCurrentContentState();
|
|
531
|
-
if (this.state !== PLAYER_STATES.STOPPED) {
|
|
532
|
-
this._priv_setPlayerState(PLAYER_STATES.STOPPED);
|
|
533
|
-
}
|
|
534
|
-
}
|
|
535
|
-
|
|
536
|
-
/**
|
|
537
|
-
* Free the resources used by the player.
|
|
538
|
-
* /!\ The player cannot be "used" anymore after this method has been called.
|
|
539
|
-
*/
|
|
540
|
-
dispose() : void {
|
|
541
|
-
// free resources linked to the loaded content
|
|
542
|
-
this.stop();
|
|
543
|
-
|
|
544
|
-
if (this.videoElement !== null) {
|
|
545
|
-
// free resources used for decryption management
|
|
546
|
-
disposeDecryptionResources(this.videoElement)
|
|
547
|
-
.catch((err : unknown) => {
|
|
548
|
-
const message = err instanceof Error ? err.message :
|
|
549
|
-
"Unknown error";
|
|
550
|
-
log.error("API: Could not dispose decryption resources: " + message);
|
|
551
|
-
});
|
|
552
|
-
}
|
|
553
|
-
|
|
554
|
-
// free resources linked to the Player instance
|
|
555
|
-
this._destroyCanceller.cancel();
|
|
556
|
-
|
|
557
|
-
this._priv_reloadingMetadata = {};
|
|
558
|
-
|
|
559
|
-
// un-attach video element
|
|
560
|
-
this.videoElement = null;
|
|
561
|
-
}
|
|
562
|
-
|
|
563
|
-
/**
|
|
564
|
-
* Load a new video.
|
|
565
|
-
* @param {Object} opts
|
|
566
|
-
*/
|
|
567
|
-
loadVideo(opts : ILoadVideoOptions) : void {
|
|
568
|
-
const options = parseLoadVideoOptions(opts);
|
|
569
|
-
log.info("API: Calling loadvideo", options.url, options.transport);
|
|
570
|
-
this._priv_reloadingMetadata = { options };
|
|
571
|
-
this._priv_initializeContentPlayback(options);
|
|
572
|
-
this._priv_lastAutoPlay = options.autoPlay;
|
|
573
|
-
}
|
|
574
|
-
|
|
575
|
-
/**
|
|
576
|
-
* Reload the last loaded content.
|
|
577
|
-
* @param {Object} reloadOpts
|
|
578
|
-
*/
|
|
579
|
-
reload(reloadOpts?: {
|
|
580
|
-
reloadAt?: { position?: number; relative?: number };
|
|
581
|
-
keySystems?: IKeySystemOption[];
|
|
582
|
-
autoPlay?: boolean;
|
|
583
|
-
}): void {
|
|
584
|
-
const { options,
|
|
585
|
-
manifest,
|
|
586
|
-
reloadPosition,
|
|
587
|
-
reloadInPause } = this._priv_reloadingMetadata;
|
|
588
|
-
if (options === undefined) {
|
|
589
|
-
throw new Error("API: Can't reload without having previously loaded a content.");
|
|
590
|
-
}
|
|
591
|
-
checkReloadOptions(reloadOpts);
|
|
592
|
-
let startAt : IParsedStartAtOption | undefined;
|
|
593
|
-
if (reloadOpts?.reloadAt?.position !== undefined) {
|
|
594
|
-
startAt = { position: reloadOpts.reloadAt.position };
|
|
595
|
-
} else if (reloadOpts?.reloadAt?.relative !== undefined) {
|
|
596
|
-
if (reloadPosition === undefined) {
|
|
597
|
-
throw new Error(
|
|
598
|
-
"Can't reload to a relative position when previous content was not loaded."
|
|
599
|
-
);
|
|
600
|
-
} else {
|
|
601
|
-
startAt = { position: reloadOpts.reloadAt.relative + reloadPosition };
|
|
602
|
-
}
|
|
603
|
-
} else if (reloadPosition !== undefined) {
|
|
604
|
-
startAt = { position: reloadPosition };
|
|
605
|
-
}
|
|
606
|
-
|
|
607
|
-
let autoPlay : boolean | undefined;
|
|
608
|
-
if (reloadOpts?.autoPlay !== undefined) {
|
|
609
|
-
autoPlay = reloadOpts.autoPlay;
|
|
610
|
-
} else if (reloadInPause !== undefined) {
|
|
611
|
-
autoPlay = !reloadInPause;
|
|
612
|
-
}
|
|
613
|
-
|
|
614
|
-
let keySystems : IKeySystemOption[] | undefined;
|
|
615
|
-
if (reloadOpts?.keySystems !== undefined) {
|
|
616
|
-
keySystems = reloadOpts.keySystems;
|
|
617
|
-
} else if (this._priv_reloadingMetadata.options?.keySystems !== undefined) {
|
|
618
|
-
keySystems = this._priv_reloadingMetadata.options.keySystems;
|
|
619
|
-
}
|
|
620
|
-
|
|
621
|
-
const newOptions = { ...options,
|
|
622
|
-
initialManifest: manifest };
|
|
623
|
-
if (startAt !== undefined) {
|
|
624
|
-
newOptions.startAt = startAt;
|
|
625
|
-
}
|
|
626
|
-
if (autoPlay !== undefined) {
|
|
627
|
-
newOptions.autoPlay = autoPlay;
|
|
628
|
-
}
|
|
629
|
-
if (keySystems !== undefined) {
|
|
630
|
-
newOptions.keySystems = keySystems;
|
|
631
|
-
}
|
|
632
|
-
this._priv_initializeContentPlayback(newOptions);
|
|
633
|
-
}
|
|
634
|
-
|
|
635
|
-
public createDebugElement(element : HTMLElement) : {
|
|
636
|
-
dispose() : void;
|
|
637
|
-
} {
|
|
638
|
-
if (features.createDebugElement === null) {
|
|
639
|
-
throw new Error("Feature `DEBUG_ELEMENT` not added to the RxPlayer");
|
|
640
|
-
}
|
|
641
|
-
const canceller = new TaskCanceller();
|
|
642
|
-
features.createDebugElement(element, this, canceller.signal);
|
|
643
|
-
return {
|
|
644
|
-
dispose() {
|
|
645
|
-
canceller.cancel();
|
|
646
|
-
},
|
|
647
|
-
};
|
|
648
|
-
}
|
|
649
|
-
|
|
650
|
-
/**
|
|
651
|
-
* From given options, initialize content playback.
|
|
652
|
-
* @param {Object} options
|
|
653
|
-
*/
|
|
654
|
-
private _priv_initializeContentPlayback(options : IParsedLoadVideoOptions) : void {
|
|
655
|
-
const { autoPlay,
|
|
656
|
-
audioTrackSwitchingMode,
|
|
657
|
-
defaultAudioTrack,
|
|
658
|
-
defaultTextTrack,
|
|
659
|
-
enableFastSwitching,
|
|
660
|
-
initialManifest,
|
|
661
|
-
keySystems,
|
|
662
|
-
lowLatencyMode,
|
|
663
|
-
manualBitrateSwitchingMode,
|
|
664
|
-
minimumManifestUpdateInterval,
|
|
665
|
-
networkConfig,
|
|
666
|
-
onCodecSwitch,
|
|
667
|
-
startAt,
|
|
668
|
-
transport,
|
|
669
|
-
transportOptions,
|
|
670
|
-
url } = options;
|
|
671
|
-
|
|
672
|
-
// Perform multiple checks on the given options
|
|
673
|
-
if (this.videoElement === null) {
|
|
674
|
-
throw new Error("the attached video element is disposed");
|
|
675
|
-
}
|
|
676
|
-
|
|
677
|
-
const isDirectFile = transport === "directfile";
|
|
678
|
-
|
|
679
|
-
/** Emit to stop the current content. */
|
|
680
|
-
const currentContentCanceller = new TaskCanceller();
|
|
681
|
-
|
|
682
|
-
const videoElement = this.videoElement;
|
|
683
|
-
|
|
684
|
-
let initializer : ContentInitializer;
|
|
685
|
-
|
|
686
|
-
let mediaElementTrackChoiceManager : MediaElementTrackChoiceManager | null =
|
|
687
|
-
null;
|
|
688
|
-
if (!isDirectFile) {
|
|
689
|
-
const transportFn = features.transports[transport];
|
|
690
|
-
if (typeof transportFn !== "function") {
|
|
691
|
-
// Stop previous content and reset its state
|
|
692
|
-
this.stop();
|
|
693
|
-
this._priv_currentError = null;
|
|
694
|
-
throw new Error(`transport "${transport}" not supported`);
|
|
695
|
-
}
|
|
696
|
-
|
|
697
|
-
if (features.mediaSourceInit === null) {
|
|
698
|
-
throw new Error("MediaSource streaming not supported");
|
|
699
|
-
}
|
|
700
|
-
|
|
701
|
-
const transportPipelines = transportFn(transportOptions);
|
|
702
|
-
|
|
703
|
-
const { offlineRetry,
|
|
704
|
-
segmentRetry,
|
|
705
|
-
manifestRetry,
|
|
706
|
-
manifestRequestTimeout,
|
|
707
|
-
segmentRequestTimeout } = networkConfig;
|
|
708
|
-
|
|
709
|
-
/** Interface used to load and refresh the Manifest. */
|
|
710
|
-
const manifestRequestSettings = { lowLatencyMode,
|
|
711
|
-
maxRetryRegular: manifestRetry,
|
|
712
|
-
maxRetryOffline: offlineRetry,
|
|
713
|
-
requestTimeout: manifestRequestTimeout,
|
|
714
|
-
minimumManifestUpdateInterval,
|
|
715
|
-
initialManifest };
|
|
716
|
-
|
|
717
|
-
const relyOnVideoVisibilityAndSize = canRelyOnVideoVisibilityAndSize();
|
|
718
|
-
const throttlers : IABRThrottlers = { throttle: {},
|
|
719
|
-
throttleBitrate: {},
|
|
720
|
-
limitWidth: {} };
|
|
721
|
-
|
|
722
|
-
if (this._priv_throttleWhenHidden) {
|
|
723
|
-
if (!relyOnVideoVisibilityAndSize) {
|
|
724
|
-
log.warn("API: Can't apply throttleWhenHidden because " +
|
|
725
|
-
"browser can't be trusted for visibility.");
|
|
726
|
-
} else {
|
|
727
|
-
throttlers.throttle = {
|
|
728
|
-
video: createMappedReference(
|
|
729
|
-
getPageActivityRef(currentContentCanceller.signal),
|
|
730
|
-
isActive => isActive ? Infinity : 0,
|
|
731
|
-
currentContentCanceller.signal),
|
|
732
|
-
};
|
|
733
|
-
}
|
|
734
|
-
}
|
|
735
|
-
if (this._priv_throttleVideoBitrateWhenHidden) {
|
|
736
|
-
if (!relyOnVideoVisibilityAndSize) {
|
|
737
|
-
log.warn("API: Can't apply throttleVideoBitrateWhenHidden because " +
|
|
738
|
-
"browser can't be trusted for visibility.");
|
|
739
|
-
} else {
|
|
740
|
-
throttlers.throttleBitrate = {
|
|
741
|
-
video: createMappedReference(
|
|
742
|
-
getVideoVisibilityRef(this._priv_pictureInPictureRef,
|
|
743
|
-
currentContentCanceller.signal),
|
|
744
|
-
isActive => isActive ? Infinity : 0,
|
|
745
|
-
currentContentCanceller.signal),
|
|
746
|
-
};
|
|
747
|
-
}
|
|
748
|
-
}
|
|
749
|
-
if (this._priv_limitVideoWidth) {
|
|
750
|
-
if (!relyOnVideoVisibilityAndSize) {
|
|
751
|
-
log.warn("API: Can't apply limitVideoWidth because browser can't be " +
|
|
752
|
-
"trusted for video size.");
|
|
753
|
-
} else {
|
|
754
|
-
throttlers.limitWidth = {
|
|
755
|
-
video: getVideoWidthRef(videoElement,
|
|
756
|
-
this._priv_pictureInPictureRef,
|
|
757
|
-
currentContentCanceller.signal),
|
|
758
|
-
};
|
|
759
|
-
}
|
|
760
|
-
}
|
|
761
|
-
|
|
762
|
-
/** Options used by the adaptive logic. */
|
|
763
|
-
const adaptiveOptions = {
|
|
764
|
-
initialBitrates: this._priv_bitrateInfos.lastBitrates,
|
|
765
|
-
lowLatencyMode,
|
|
766
|
-
manualBitrates: this._priv_bitrateInfos.manualBitrates,
|
|
767
|
-
minAutoBitrates: this._priv_bitrateInfos.minAutoBitrates,
|
|
768
|
-
maxAutoBitrates: this._priv_bitrateInfos.maxAutoBitrates,
|
|
769
|
-
throttlers,
|
|
770
|
-
};
|
|
771
|
-
|
|
772
|
-
/** Options used by the TextTrack SegmentBuffer. */
|
|
773
|
-
const textTrackOptions = options.textTrackMode === "native" ?
|
|
774
|
-
{ textTrackMode: "native" as const,
|
|
775
|
-
hideNativeSubtitle: options.hideNativeSubtitle } :
|
|
776
|
-
{ textTrackMode: "html" as const,
|
|
777
|
-
textTrackElement: options.textTrackElement };
|
|
778
|
-
|
|
779
|
-
const bufferOptions = objectAssign({ audioTrackSwitchingMode,
|
|
780
|
-
enableFastSwitching,
|
|
781
|
-
manualBitrateSwitchingMode,
|
|
782
|
-
onCodecSwitch },
|
|
783
|
-
this._priv_bufferOptions);
|
|
784
|
-
|
|
785
|
-
const segmentRequestOptions = { lowLatencyMode,
|
|
786
|
-
maxRetryRegular: segmentRetry,
|
|
787
|
-
requestTimeout: segmentRequestTimeout,
|
|
788
|
-
maxRetryOffline: offlineRetry };
|
|
789
|
-
|
|
790
|
-
initializer = new features.mediaSourceInit({
|
|
791
|
-
adaptiveOptions,
|
|
792
|
-
autoPlay,
|
|
793
|
-
bufferOptions,
|
|
794
|
-
keySystems,
|
|
795
|
-
lowLatencyMode,
|
|
796
|
-
manifestRequestSettings,
|
|
797
|
-
transport: transportPipelines,
|
|
798
|
-
segmentRequestOptions,
|
|
799
|
-
speed: this._priv_speed,
|
|
800
|
-
startAt,
|
|
801
|
-
textTrackOptions,
|
|
802
|
-
url,
|
|
803
|
-
});
|
|
804
|
-
} else {
|
|
805
|
-
if (features.directfile === null) {
|
|
806
|
-
this.stop();
|
|
807
|
-
this._priv_currentError = null;
|
|
808
|
-
throw new Error("DirectFile feature not activated in your build.");
|
|
809
|
-
} else if (isNullOrUndefined(url)) {
|
|
810
|
-
throw new Error("No URL for a DirectFile content");
|
|
811
|
-
}
|
|
812
|
-
mediaElementTrackChoiceManager =
|
|
813
|
-
this._priv_initializeMediaElementTrackChoiceManager(
|
|
814
|
-
defaultAudioTrack,
|
|
815
|
-
defaultTextTrack,
|
|
816
|
-
currentContentCanceller.signal
|
|
817
|
-
);
|
|
818
|
-
if (currentContentCanceller.isUsed()) {
|
|
819
|
-
return;
|
|
820
|
-
}
|
|
821
|
-
initializer = new features.directfile.initDirectFile({ autoPlay,
|
|
822
|
-
keySystems,
|
|
823
|
-
speed: this._priv_speed,
|
|
824
|
-
startAt,
|
|
825
|
-
url });
|
|
826
|
-
}
|
|
827
|
-
|
|
828
|
-
/** Future `this._priv_contentInfos` related to this content. */
|
|
829
|
-
const contentInfos : IPublicApiContentInfos = {
|
|
830
|
-
contentId: generateContentId(),
|
|
831
|
-
originalUrl: url,
|
|
832
|
-
currentContentCanceller,
|
|
833
|
-
initializer,
|
|
834
|
-
isDirectFile,
|
|
835
|
-
segmentBuffersStore: null,
|
|
836
|
-
thumbnails: null,
|
|
837
|
-
manifest: null,
|
|
838
|
-
currentPeriod: null,
|
|
839
|
-
activeAdaptations: null,
|
|
840
|
-
activeRepresentations: null,
|
|
841
|
-
initialAudioTrack: defaultAudioTrack,
|
|
842
|
-
initialTextTrack: defaultTextTrack,
|
|
843
|
-
trackChoiceManager: null,
|
|
844
|
-
mediaElementTrackChoiceManager,
|
|
845
|
-
};
|
|
846
|
-
|
|
847
|
-
// Bind events
|
|
848
|
-
initializer.addEventListener("error", (error) => {
|
|
849
|
-
const formattedError = formatError(error, {
|
|
850
|
-
defaultCode: "NONE",
|
|
851
|
-
defaultReason: "An unknown error stopped content playback.",
|
|
852
|
-
});
|
|
853
|
-
formattedError.fatal = true;
|
|
854
|
-
|
|
855
|
-
contentInfos.currentContentCanceller.cancel();
|
|
856
|
-
this._priv_cleanUpCurrentContentState();
|
|
857
|
-
this._priv_currentError = formattedError;
|
|
858
|
-
log.error("API: The player stopped because of an error",
|
|
859
|
-
error instanceof Error ? error : "");
|
|
860
|
-
this._priv_setPlayerState(PLAYER_STATES.STOPPED);
|
|
861
|
-
|
|
862
|
-
// TODO This condition is here because the eventual callback called when the
|
|
863
|
-
// player state is updated can launch a new content, thus the error will not
|
|
864
|
-
// be here anymore, in which case triggering the "error" event is unwanted.
|
|
865
|
-
// This is very ugly though, and we should probable have a better solution
|
|
866
|
-
if (this._priv_currentError === formattedError) {
|
|
867
|
-
this.trigger("error", formattedError);
|
|
868
|
-
}
|
|
869
|
-
});
|
|
870
|
-
initializer.addEventListener("warning", (error) => {
|
|
871
|
-
const formattedError = formatError(error, {
|
|
872
|
-
defaultCode: "NONE",
|
|
873
|
-
defaultReason: "An unknown error happened.",
|
|
874
|
-
});
|
|
875
|
-
log.warn("API: Sending warning:", formattedError);
|
|
876
|
-
this.trigger("warning", formattedError);
|
|
877
|
-
});
|
|
878
|
-
initializer.addEventListener("reloadingMediaSource", (payload) => {
|
|
879
|
-
contentInfos.segmentBuffersStore = null;
|
|
880
|
-
if (contentInfos.trackChoiceManager !== null) {
|
|
881
|
-
contentInfos.trackChoiceManager.resetPeriods();
|
|
882
|
-
}
|
|
883
|
-
this._priv_lastAutoPlay = payload.autoPlay;
|
|
884
|
-
});
|
|
885
|
-
initializer.addEventListener("inbandEvents", (inbandEvents) =>
|
|
886
|
-
this.trigger("inbandEvents", inbandEvents));
|
|
887
|
-
initializer.addEventListener("streamEvent", (streamEvent) =>
|
|
888
|
-
this.trigger("streamEvent", streamEvent));
|
|
889
|
-
initializer.addEventListener("streamEventSkip", (streamEventSkip) =>
|
|
890
|
-
this.trigger("streamEventSkip", streamEventSkip));
|
|
891
|
-
initializer.addEventListener("decipherabilityUpdate", (decipherabilityUpdate) =>
|
|
892
|
-
this.trigger("decipherabilityUpdate", decipherabilityUpdate));
|
|
893
|
-
initializer.addEventListener("activePeriodChanged", (periodInfo) =>
|
|
894
|
-
this._priv_onActivePeriodChanged(contentInfos, periodInfo));
|
|
895
|
-
initializer.addEventListener("periodStreamReady", (periodReadyInfo) =>
|
|
896
|
-
this._priv_onPeriodStreamReady(contentInfos, periodReadyInfo));
|
|
897
|
-
initializer.addEventListener("periodStreamCleared", (periodClearedInfo) =>
|
|
898
|
-
this._priv_onPeriodStreamCleared(contentInfos, periodClearedInfo));
|
|
899
|
-
initializer.addEventListener("representationChange", (representationInfo) =>
|
|
900
|
-
this._priv_onRepresentationChange(contentInfos, representationInfo));
|
|
901
|
-
initializer.addEventListener("adaptationChange", (adaptationInfo) =>
|
|
902
|
-
this._priv_onAdaptationChange(contentInfos, adaptationInfo));
|
|
903
|
-
initializer.addEventListener("bitrateEstimationChange", (bitrateEstimationInfo) =>
|
|
904
|
-
this._priv_onBitrateEstimationChange(bitrateEstimationInfo));
|
|
905
|
-
initializer.addEventListener("manifestReady", (manifest) =>
|
|
906
|
-
this._priv_onManifestReady(contentInfos, manifest));
|
|
907
|
-
initializer.addEventListener("loaded", (evt) => {
|
|
908
|
-
contentInfos.segmentBuffersStore = evt.segmentBuffersStore;
|
|
909
|
-
});
|
|
910
|
-
initializer.addEventListener("addedSegment", (evt) => {
|
|
911
|
-
// Manage image tracks
|
|
912
|
-
// @deprecated
|
|
913
|
-
const { content, segmentData } = evt;
|
|
914
|
-
if (content.adaptation.type === "image") {
|
|
915
|
-
if (!isNullOrUndefined(segmentData) &&
|
|
916
|
-
(segmentData as { type : string }).type === "bif")
|
|
917
|
-
{
|
|
918
|
-
const imageData = (segmentData as { data : IBifThumbnail[] }).data;
|
|
919
|
-
/* eslint-disable import/no-deprecated */
|
|
920
|
-
contentInfos.thumbnails = imageData;
|
|
921
|
-
this.trigger("imageTrackUpdate",
|
|
922
|
-
{ data: contentInfos.thumbnails });
|
|
923
|
-
/* eslint-enable import/no-deprecated */
|
|
924
|
-
}
|
|
925
|
-
}
|
|
926
|
-
});
|
|
927
|
-
|
|
928
|
-
// Now, that most events are linked, prepare the next content.
|
|
929
|
-
initializer.prepare();
|
|
930
|
-
|
|
931
|
-
// Now that the content is prepared, stop previous content and reset state
|
|
932
|
-
// This is done after content preparation as `stop` could technically have
|
|
933
|
-
// a long and synchronous blocking time.
|
|
934
|
-
// Note that this call is done **synchronously** after all events linking.
|
|
935
|
-
// This is **VERY** important so:
|
|
936
|
-
// - the `STOPPED` state is switched to synchronously after loading a new
|
|
937
|
-
// content.
|
|
938
|
-
// - we can avoid involontarily catching events linked to the previous
|
|
939
|
-
// content.
|
|
940
|
-
this.stop();
|
|
941
|
-
|
|
942
|
-
/** Global "playback observer" which will emit playback conditions */
|
|
943
|
-
const playbackObserver = new PlaybackObserver(videoElement, {
|
|
944
|
-
withMediaSource: !isDirectFile,
|
|
945
|
-
lowLatencyMode,
|
|
946
|
-
});
|
|
947
|
-
|
|
948
|
-
currentContentCanceller.signal.register(() => {
|
|
949
|
-
playbackObserver.stop();
|
|
950
|
-
});
|
|
951
|
-
|
|
952
|
-
// Update the RxPlayer's state at the right events
|
|
953
|
-
const playerStateRef = constructPlayerStateReference(initializer,
|
|
954
|
-
videoElement,
|
|
955
|
-
playbackObserver,
|
|
956
|
-
currentContentCanceller.signal);
|
|
957
|
-
currentContentCanceller.signal.register(() => {
|
|
958
|
-
initializer.dispose();
|
|
959
|
-
});
|
|
960
|
-
|
|
961
|
-
/**
|
|
962
|
-
* Function updating `this._priv_reloadingMetadata` in function of the
|
|
963
|
-
* current state and playback conditions.
|
|
964
|
-
* To call when either might change.
|
|
965
|
-
* @param {string} state - The player state we're about to switch to.
|
|
966
|
-
*/
|
|
967
|
-
const updateReloadingMetadata = (state : IPlayerState) => {
|
|
968
|
-
switch (state) {
|
|
969
|
-
case "STOPPED":
|
|
970
|
-
case "RELOADING":
|
|
971
|
-
case "LOADING":
|
|
972
|
-
break; // keep previous metadata
|
|
973
|
-
case "ENDED":
|
|
974
|
-
this._priv_reloadingMetadata.reloadInPause = true;
|
|
975
|
-
this._priv_reloadingMetadata.reloadPosition =
|
|
976
|
-
playbackObserver.getReference().getValue().position;
|
|
977
|
-
break;
|
|
978
|
-
default:
|
|
979
|
-
const o = playbackObserver.getReference().getValue();
|
|
980
|
-
this._priv_reloadingMetadata.reloadInPause = o.paused;
|
|
981
|
-
this._priv_reloadingMetadata.reloadPosition = o.position;
|
|
982
|
-
break;
|
|
983
|
-
}
|
|
984
|
-
};
|
|
985
|
-
|
|
986
|
-
/**
|
|
987
|
-
* `TaskCanceller` allowing to stop emitting `"play"` and `"pause"`
|
|
988
|
-
* events.
|
|
989
|
-
* `null` when such events are not emitted currently.
|
|
990
|
-
*/
|
|
991
|
-
let playPauseEventsCanceller : TaskCanceller | null = null;
|
|
992
|
-
|
|
993
|
-
/**
|
|
994
|
-
* Callback emitting `"play"` and `"pause`" events once the content is
|
|
995
|
-
* loaded, starting from the state indicated in argument.
|
|
996
|
-
* @param {boolean} willAutoPlay - If `false`, we're currently paused.
|
|
997
|
-
*/
|
|
998
|
-
const triggerPlayPauseEventsWhenReady = (willAutoPlay: boolean) => {
|
|
999
|
-
if (playPauseEventsCanceller !== null) {
|
|
1000
|
-
playPauseEventsCanceller.cancel(); // cancel previous logic
|
|
1001
|
-
playPauseEventsCanceller = null;
|
|
1002
|
-
}
|
|
1003
|
-
playerStateRef.onUpdate((val, stopListeningToStateUpdates) => {
|
|
1004
|
-
if (!isLoadedState(val)) {
|
|
1005
|
-
return; // content not loaded yet: no event
|
|
1006
|
-
}
|
|
1007
|
-
stopListeningToStateUpdates();
|
|
1008
|
-
if (playPauseEventsCanceller !== null) {
|
|
1009
|
-
playPauseEventsCanceller.cancel();
|
|
1010
|
-
}
|
|
1011
|
-
playPauseEventsCanceller = new TaskCanceller();
|
|
1012
|
-
playPauseEventsCanceller.linkToSignal(currentContentCanceller.signal);
|
|
1013
|
-
if (willAutoPlay !== !videoElement.paused) {
|
|
1014
|
-
// paused status is not at the expected value on load: emit event
|
|
1015
|
-
if (videoElement.paused) {
|
|
1016
|
-
this.trigger("pause", null);
|
|
1017
|
-
} else {
|
|
1018
|
-
this.trigger("play", null);
|
|
1019
|
-
}
|
|
1020
|
-
}
|
|
1021
|
-
emitPlayPauseEvents(videoElement,
|
|
1022
|
-
() => this.trigger("play", null),
|
|
1023
|
-
() => this.trigger("pause", null),
|
|
1024
|
-
currentContentCanceller.signal);
|
|
1025
|
-
}, { emitCurrentValue: false, clearSignal: currentContentCanceller.signal });
|
|
1026
|
-
};
|
|
1027
|
-
|
|
1028
|
-
triggerPlayPauseEventsWhenReady(autoPlay);
|
|
1029
|
-
initializer.addEventListener("reloadingMediaSource", (payload) => {
|
|
1030
|
-
triggerPlayPauseEventsWhenReady(payload.autoPlay);
|
|
1031
|
-
});
|
|
1032
|
-
|
|
1033
|
-
/**
|
|
1034
|
-
* `TaskCanceller` allowing to stop emitting `"seeking"` and `"seeked"`
|
|
1035
|
-
* events.
|
|
1036
|
-
* `null` when such events are not emitted currently.
|
|
1037
|
-
*/
|
|
1038
|
-
let seekEventsCanceller : TaskCanceller | null = null;
|
|
1039
|
-
|
|
1040
|
-
// React to player state change
|
|
1041
|
-
playerStateRef.onUpdate((newState : IPlayerState) => {
|
|
1042
|
-
updateReloadingMetadata(newState);
|
|
1043
|
-
this._priv_setPlayerState(newState);
|
|
1044
|
-
|
|
1045
|
-
if (currentContentCanceller.isUsed()) {
|
|
1046
|
-
return;
|
|
1047
|
-
}
|
|
1048
|
-
|
|
1049
|
-
if (seekEventsCanceller !== null) {
|
|
1050
|
-
if (!isLoadedState(this.state)) {
|
|
1051
|
-
seekEventsCanceller.cancel();
|
|
1052
|
-
seekEventsCanceller = null;
|
|
1053
|
-
}
|
|
1054
|
-
} else if (isLoadedState(this.state)) {
|
|
1055
|
-
seekEventsCanceller = new TaskCanceller();
|
|
1056
|
-
seekEventsCanceller.linkToSignal(currentContentCanceller.signal);
|
|
1057
|
-
emitSeekEvents(videoElement,
|
|
1058
|
-
playbackObserver,
|
|
1059
|
-
() => this.trigger("seeking", null),
|
|
1060
|
-
() => this.trigger("seeked", null),
|
|
1061
|
-
seekEventsCanceller.signal);
|
|
1062
|
-
}
|
|
1063
|
-
|
|
1064
|
-
// Previous call could have performed all kind of side-effects, thus,
|
|
1065
|
-
// we re-check the current state associated to the RxPlayer
|
|
1066
|
-
if (this.state === PLAYER_STATES.ENDED && this._priv_stopAtEnd) {
|
|
1067
|
-
this.stop();
|
|
1068
|
-
}
|
|
1069
|
-
}, { emitCurrentValue: true, clearSignal: currentContentCanceller.signal });
|
|
1070
|
-
|
|
1071
|
-
// React to playback conditions change
|
|
1072
|
-
playbackObserver.listen((observation) => {
|
|
1073
|
-
updateReloadingMetadata(this.state);
|
|
1074
|
-
this._priv_triggerPositionUpdate(contentInfos, observation);
|
|
1075
|
-
}, { clearSignal: currentContentCanceller.signal });
|
|
1076
|
-
|
|
1077
|
-
this._priv_currentError = null;
|
|
1078
|
-
this._priv_contentInfos = contentInfos;
|
|
1079
|
-
|
|
1080
|
-
currentContentCanceller.signal.register(() => {
|
|
1081
|
-
initializer.removeEventListener();
|
|
1082
|
-
});
|
|
1083
|
-
|
|
1084
|
-
// initialize the content only when the lock is inactive
|
|
1085
|
-
this._priv_contentLock.onUpdate((isLocked, stopListeningToLock) => {
|
|
1086
|
-
if (!isLocked) {
|
|
1087
|
-
stopListeningToLock();
|
|
1088
|
-
|
|
1089
|
-
// start playback!
|
|
1090
|
-
initializer.start(videoElement, playbackObserver);
|
|
1091
|
-
}
|
|
1092
|
-
}, { emitCurrentValue: true, clearSignal: currentContentCanceller.signal });
|
|
1093
|
-
}
|
|
1094
|
-
|
|
1095
|
-
/**
|
|
1096
|
-
* Returns fatal error if one for the current content.
|
|
1097
|
-
* null otherwise.
|
|
1098
|
-
* @returns {Object|null} - The current Error (`null` when no error).
|
|
1099
|
-
*/
|
|
1100
|
-
getError() : Error|null {
|
|
1101
|
-
return this._priv_currentError;
|
|
1102
|
-
}
|
|
1103
|
-
|
|
1104
|
-
/**
|
|
1105
|
-
* Returns manifest/playlist object.
|
|
1106
|
-
* null if the player is STOPPED.
|
|
1107
|
-
* @deprecated
|
|
1108
|
-
* @returns {Manifest|null} - The current Manifest (`null` when not known).
|
|
1109
|
-
*/
|
|
1110
|
-
getManifest() : Manifest|null {
|
|
1111
|
-
warnOnce("getManifest is deprecated." +
|
|
1112
|
-
" Please open an issue if you used this API.");
|
|
1113
|
-
if (this._priv_contentInfos === null) {
|
|
1114
|
-
return null;
|
|
1115
|
-
}
|
|
1116
|
-
return this._priv_contentInfos.manifest;
|
|
1117
|
-
}
|
|
1118
|
-
|
|
1119
|
-
/**
|
|
1120
|
-
* Returns Adaptations (tracks) for every currently playing type
|
|
1121
|
-
* (audio/video/text...).
|
|
1122
|
-
* @deprecated
|
|
1123
|
-
* @returns {Object|null} - The current Adaptation objects, per type (`null`
|
|
1124
|
-
* when none is known for now.
|
|
1125
|
-
*/
|
|
1126
|
-
getCurrentAdaptations(
|
|
1127
|
-
) : Partial<Record<IBufferType, IAdaptation|null>> | null {
|
|
1128
|
-
warnOnce("getCurrentAdaptations is deprecated." +
|
|
1129
|
-
" Please open an issue if you used this API.");
|
|
1130
|
-
if (this._priv_contentInfos === null) {
|
|
1131
|
-
return null;
|
|
1132
|
-
}
|
|
1133
|
-
const { currentPeriod, activeAdaptations } = this._priv_contentInfos;
|
|
1134
|
-
if (currentPeriod === null ||
|
|
1135
|
-
activeAdaptations === null ||
|
|
1136
|
-
isNullOrUndefined(activeAdaptations[currentPeriod.id]))
|
|
1137
|
-
{
|
|
1138
|
-
return null;
|
|
1139
|
-
}
|
|
1140
|
-
return activeAdaptations[currentPeriod.id];
|
|
1141
|
-
}
|
|
1142
|
-
|
|
1143
|
-
/**
|
|
1144
|
-
* Returns representations (qualities) for every currently playing type
|
|
1145
|
-
* (audio/video/text...).
|
|
1146
|
-
* @deprecated
|
|
1147
|
-
* @returns {Object|null} - The current Representation objects, per type
|
|
1148
|
-
* (`null` when none is known for now.
|
|
1149
|
-
*/
|
|
1150
|
-
getCurrentRepresentations(
|
|
1151
|
-
) : Partial<Record<IBufferType, IRepresentation|null>> | null {
|
|
1152
|
-
warnOnce("getCurrentRepresentations is deprecated." +
|
|
1153
|
-
" Please open an issue if you used this API.");
|
|
1154
|
-
return this._priv_getCurrentRepresentations();
|
|
1155
|
-
}
|
|
1156
|
-
|
|
1157
|
-
/**
|
|
1158
|
-
* Returns the media DOM element used by the player.
|
|
1159
|
-
* You should not its HTML5 API directly and use the player's method instead,
|
|
1160
|
-
* to ensure a well-behaved player.
|
|
1161
|
-
* @returns {HTMLMediaElement|null} - The HTMLMediaElement used (`null` when
|
|
1162
|
-
* disposed)
|
|
1163
|
-
*/
|
|
1164
|
-
getVideoElement() : HTMLMediaElement|null {
|
|
1165
|
-
return this.videoElement;
|
|
1166
|
-
}
|
|
1167
|
-
|
|
1168
|
-
/**
|
|
1169
|
-
* If one returns the first native text-track element attached to the media element.
|
|
1170
|
-
* @deprecated
|
|
1171
|
-
* @returns {TextTrack} - The native TextTrack attached (`null` when none)
|
|
1172
|
-
*/
|
|
1173
|
-
getNativeTextTrack() : TextTrack|null {
|
|
1174
|
-
warnOnce("getNativeTextTrack is deprecated." +
|
|
1175
|
-
" Please open an issue if you used this API.");
|
|
1176
|
-
if (this.videoElement === null) {
|
|
1177
|
-
throw new Error("Disposed player");
|
|
1178
|
-
}
|
|
1179
|
-
const videoElement = this.videoElement;
|
|
1180
|
-
const textTracks = videoElement.textTracks;
|
|
1181
|
-
if (textTracks.length > 0) {
|
|
1182
|
-
return videoElement.textTracks[0];
|
|
1183
|
-
} else {
|
|
1184
|
-
return null;
|
|
1185
|
-
}
|
|
1186
|
-
}
|
|
1187
|
-
|
|
1188
|
-
/**
|
|
1189
|
-
* Returns the player's current state.
|
|
1190
|
-
* @returns {string} - The current Player's state
|
|
1191
|
-
*/
|
|
1192
|
-
getPlayerState() : string {
|
|
1193
|
-
return this.state;
|
|
1194
|
-
}
|
|
1195
|
-
|
|
1196
|
-
/**
|
|
1197
|
-
* Returns true if a content is loaded.
|
|
1198
|
-
* @returns {Boolean} - `true` if a content is loaded, `false` otherwise.
|
|
1199
|
-
*/
|
|
1200
|
-
isContentLoaded() : boolean {
|
|
1201
|
-
return !arrayIncludes(["LOADING", "RELOADING", "STOPPED"], this.state);
|
|
1202
|
-
}
|
|
1203
|
-
|
|
1204
|
-
/**
|
|
1205
|
-
* Returns true if the player is buffering.
|
|
1206
|
-
* @returns {Boolean} - `true` if the player is buffering, `false` otherwise.
|
|
1207
|
-
*/
|
|
1208
|
-
isBuffering() : boolean {
|
|
1209
|
-
return arrayIncludes(["BUFFERING", "SEEKING", "LOADING", "RELOADING"], this.state);
|
|
1210
|
-
}
|
|
1211
|
-
|
|
1212
|
-
/**
|
|
1213
|
-
* Returns the play/pause status of the player :
|
|
1214
|
-
* - when `LOADING` or `RELOADING`, returns the scheduled play/pause condition
|
|
1215
|
-
* for when loading is over,
|
|
1216
|
-
* - in other states, returns the `<video>` element .paused value,
|
|
1217
|
-
* - if the player is disposed, returns `true`.
|
|
1218
|
-
* @returns {Boolean} - `true` if the player is paused or will be after loading,
|
|
1219
|
-
* `false` otherwise.
|
|
1220
|
-
*/
|
|
1221
|
-
isPaused() : boolean {
|
|
1222
|
-
if (this.videoElement) {
|
|
1223
|
-
if (arrayIncludes(["LOADING", "RELOADING"], this.state)) {
|
|
1224
|
-
return !this._priv_lastAutoPlay;
|
|
1225
|
-
} else {
|
|
1226
|
-
return this.videoElement.paused;
|
|
1227
|
-
}
|
|
1228
|
-
}
|
|
1229
|
-
return true;
|
|
1230
|
-
}
|
|
1231
|
-
|
|
1232
|
-
/**
|
|
1233
|
-
* Returns true if both:
|
|
1234
|
-
* - a content is loaded
|
|
1235
|
-
* - the content loaded is a live content
|
|
1236
|
-
* @returns {Boolean} - `true` if we're playing a live content, `false` otherwise.
|
|
1237
|
-
*/
|
|
1238
|
-
isLive() : boolean {
|
|
1239
|
-
if (this._priv_contentInfos === null) {
|
|
1240
|
-
return false;
|
|
1241
|
-
}
|
|
1242
|
-
const { isDirectFile, manifest } = this._priv_contentInfos;
|
|
1243
|
-
if (isDirectFile || manifest === null) {
|
|
1244
|
-
return false;
|
|
1245
|
-
}
|
|
1246
|
-
return manifest.isLive;
|
|
1247
|
-
}
|
|
1248
|
-
|
|
1249
|
-
/**
|
|
1250
|
-
* Returns `true` if trickmode playback is active (usually through the usage
|
|
1251
|
-
* of the `setPlaybackRate` method), which means that the RxPlayer selects
|
|
1252
|
-
* "trickmode" video tracks in priority.
|
|
1253
|
-
* @returns {Boolean}
|
|
1254
|
-
*/
|
|
1255
|
-
areTrickModeTracksEnabled(): boolean {
|
|
1256
|
-
return this._priv_preferTrickModeTracks;
|
|
1257
|
-
}
|
|
1258
|
-
|
|
1259
|
-
/**
|
|
1260
|
-
* Returns the url of the currently considered Manifest, or of the content for
|
|
1261
|
-
* directfile content.
|
|
1262
|
-
* @returns {string|undefined} - Current URL. `undefined` if not known or no
|
|
1263
|
-
* URL yet.
|
|
1264
|
-
*/
|
|
1265
|
-
getUrl() : string|undefined {
|
|
1266
|
-
if (this._priv_contentInfos === null) {
|
|
1267
|
-
return undefined;
|
|
1268
|
-
}
|
|
1269
|
-
const { isDirectFile, manifest, originalUrl } = this._priv_contentInfos;
|
|
1270
|
-
if (isDirectFile) {
|
|
1271
|
-
return originalUrl;
|
|
1272
|
-
}
|
|
1273
|
-
if (manifest !== null) {
|
|
1274
|
-
return manifest.getUrl();
|
|
1275
|
-
}
|
|
1276
|
-
return undefined;
|
|
1277
|
-
}
|
|
1278
|
-
|
|
1279
|
-
/**
|
|
1280
|
-
* Update URL of the content currently being played (e.g. DASH's MPD).
|
|
1281
|
-
* @param {Array.<string>|undefined} urls - URLs to reach that content /
|
|
1282
|
-
* Manifest from the most prioritized URL to the least prioritized URL.
|
|
1283
|
-
* @param {Object|undefined} [params]
|
|
1284
|
-
* @param {boolean} params.refresh - If `true` the resource in question
|
|
1285
|
-
* (e.g. DASH's MPD) will be refreshed immediately.
|
|
1286
|
-
*/
|
|
1287
|
-
public updateContentUrls(
|
|
1288
|
-
urls : string[] | undefined,
|
|
1289
|
-
params? : { refresh?: boolean } | undefined
|
|
1290
|
-
) : void {
|
|
1291
|
-
if (this._priv_contentInfos === null) {
|
|
1292
|
-
throw new Error("No content loaded");
|
|
1293
|
-
}
|
|
1294
|
-
const refreshNow = params?.refresh === true;
|
|
1295
|
-
this._priv_contentInfos.initializer.updateContentUrls(urls, refreshNow);
|
|
1296
|
-
}
|
|
1297
|
-
|
|
1298
|
-
/**
|
|
1299
|
-
* Returns the video duration, in seconds.
|
|
1300
|
-
* NaN if no video is playing.
|
|
1301
|
-
* @returns {Number}
|
|
1302
|
-
*/
|
|
1303
|
-
getVideoDuration() : number {
|
|
1304
|
-
if (this.videoElement === null) {
|
|
1305
|
-
throw new Error("Disposed player");
|
|
1306
|
-
}
|
|
1307
|
-
return this.videoElement.duration;
|
|
1308
|
-
}
|
|
1309
|
-
|
|
1310
|
-
/**
|
|
1311
|
-
* Returns in seconds the difference between:
|
|
1312
|
-
* - the end of the current contiguous loaded range.
|
|
1313
|
-
* - the current time
|
|
1314
|
-
* @returns {Number}
|
|
1315
|
-
*/
|
|
1316
|
-
getVideoBufferGap() : number {
|
|
1317
|
-
if (this.videoElement === null) {
|
|
1318
|
-
throw new Error("Disposed player");
|
|
1319
|
-
}
|
|
1320
|
-
const videoElement = this.videoElement;
|
|
1321
|
-
return getLeftSizeOfRange(videoElement.buffered, videoElement.currentTime);
|
|
1322
|
-
}
|
|
1323
|
-
|
|
1324
|
-
/**
|
|
1325
|
-
* Returns in seconds the difference between:
|
|
1326
|
-
* - the end of the current contiguous loaded range.
|
|
1327
|
-
* - the start of the current contiguous loaded range.
|
|
1328
|
-
* @returns {Number}
|
|
1329
|
-
*/
|
|
1330
|
-
getVideoLoadedTime() : number {
|
|
1331
|
-
warnOnce("`getVideoLoadedTime` is deprecated and won't be present in the " +
|
|
1332
|
-
"next major version");
|
|
1333
|
-
if (this.videoElement === null) {
|
|
1334
|
-
throw new Error("Disposed player");
|
|
1335
|
-
}
|
|
1336
|
-
const videoElement = this.videoElement;
|
|
1337
|
-
return getSizeOfRange(videoElement.buffered, videoElement.currentTime);
|
|
1338
|
-
}
|
|
1339
|
-
|
|
1340
|
-
/**
|
|
1341
|
-
* Returns in seconds the difference between:
|
|
1342
|
-
* - the current time.
|
|
1343
|
-
* - the start of the current contiguous loaded range.
|
|
1344
|
-
* @returns {Number}
|
|
1345
|
-
*/
|
|
1346
|
-
getVideoPlayedTime() : number {
|
|
1347
|
-
warnOnce("`getVideoPlayedTime` is deprecated and won't be present in the " +
|
|
1348
|
-
"next major version");
|
|
1349
|
-
if (this.videoElement === null) {
|
|
1350
|
-
throw new Error("Disposed player");
|
|
1351
|
-
}
|
|
1352
|
-
const videoElement = this.videoElement;
|
|
1353
|
-
return getPlayedSizeOfRange(videoElement.buffered, videoElement.currentTime);
|
|
1354
|
-
}
|
|
1355
|
-
|
|
1356
|
-
/**
|
|
1357
|
-
* Get the current position, in s, in wall-clock time.
|
|
1358
|
-
* That is:
|
|
1359
|
-
* - for live content, get a timestamp, in s, of the current played content.
|
|
1360
|
-
* - for static content, returns the position from beginning in s.
|
|
1361
|
-
*
|
|
1362
|
-
* If you do not know if you want to use this method or getPosition:
|
|
1363
|
-
* - If what you want is to display the current time to the user, use this
|
|
1364
|
-
* one.
|
|
1365
|
-
* - If what you want is to interact with the player's API or perform other
|
|
1366
|
-
* actions (like statistics) with the real player data, use getPosition.
|
|
1367
|
-
*
|
|
1368
|
-
* @returns {Number}
|
|
1369
|
-
*/
|
|
1370
|
-
getWallClockTime() : number {
|
|
1371
|
-
if (this.videoElement === null) {
|
|
1372
|
-
throw new Error("Disposed player");
|
|
1373
|
-
}
|
|
1374
|
-
if (this._priv_contentInfos === null) {
|
|
1375
|
-
return this.videoElement.currentTime;
|
|
1376
|
-
}
|
|
1377
|
-
|
|
1378
|
-
const { isDirectFile, manifest } = this._priv_contentInfos;
|
|
1379
|
-
if (isDirectFile) {
|
|
1380
|
-
const startDate = getStartDate(this.videoElement);
|
|
1381
|
-
return (startDate ?? 0) + this.videoElement.currentTime;
|
|
1382
|
-
}
|
|
1383
|
-
if (manifest !== null) {
|
|
1384
|
-
const currentTime = this.videoElement.currentTime;
|
|
1385
|
-
const ast = manifest.availabilityStartTime !== undefined ?
|
|
1386
|
-
manifest.availabilityStartTime :
|
|
1387
|
-
0;
|
|
1388
|
-
return currentTime + ast;
|
|
1389
|
-
}
|
|
1390
|
-
return 0;
|
|
1391
|
-
}
|
|
1392
|
-
|
|
1393
|
-
/**
|
|
1394
|
-
* Get the current position, in seconds, of the video element.
|
|
1395
|
-
*
|
|
1396
|
-
* If you do not know if you want to use this method or getWallClockTime:
|
|
1397
|
-
* - If what you want is to display the current time to the user, use
|
|
1398
|
-
* getWallClockTime.
|
|
1399
|
-
* - If what you want is to interact with the player's API or perform other
|
|
1400
|
-
* actions (like statistics) with the real player data, use this one.
|
|
1401
|
-
*
|
|
1402
|
-
* @returns {Number}
|
|
1403
|
-
*/
|
|
1404
|
-
getPosition() : number {
|
|
1405
|
-
if (this.videoElement === null) {
|
|
1406
|
-
throw new Error("Disposed player");
|
|
1407
|
-
}
|
|
1408
|
-
return this.videoElement.currentTime;
|
|
1409
|
-
}
|
|
1410
|
-
|
|
1411
|
-
/**
|
|
1412
|
-
* Returns the last stored content position, in seconds.
|
|
1413
|
-
*
|
|
1414
|
-
* @returns {number|undefined}
|
|
1415
|
-
*/
|
|
1416
|
-
getLastStoredContentPosition() : number|undefined {
|
|
1417
|
-
return this._priv_reloadingMetadata.reloadPosition;
|
|
1418
|
-
}
|
|
1419
|
-
|
|
1420
|
-
/**
|
|
1421
|
-
* Returns the current playback rate at which the video plays.
|
|
1422
|
-
* @returns {Number}
|
|
1423
|
-
*/
|
|
1424
|
-
getPlaybackRate() : number {
|
|
1425
|
-
return this._priv_speed.getValue();
|
|
1426
|
-
}
|
|
1427
|
-
|
|
1428
|
-
/**
|
|
1429
|
-
* Update the playback rate of the video.
|
|
1430
|
-
*
|
|
1431
|
-
* This method's effect is persisted from content to content, and can be
|
|
1432
|
-
* called even when no content is playing (it will still have an effect for
|
|
1433
|
-
* the next contents).
|
|
1434
|
-
*
|
|
1435
|
-
* If you want to reverse effects provoked by `setPlaybackRate` before playing
|
|
1436
|
-
* another content, you will have to call `setPlaybackRate` first with the
|
|
1437
|
-
* default settings you want to set.
|
|
1438
|
-
*
|
|
1439
|
-
* As an example, to reset the speed to "normal" (x1) speed and to disable
|
|
1440
|
-
* trickMode video tracks (which may have been enabled by a previous
|
|
1441
|
-
* `setPlaybackRate` call), you can call:
|
|
1442
|
-
* ```js
|
|
1443
|
-
* player.setPlaybackRate(1, { preferTrickModeTracks: false });
|
|
1444
|
-
* ```
|
|
1445
|
-
*
|
|
1446
|
-
* --
|
|
1447
|
-
*
|
|
1448
|
-
* This method can be used to switch to or exit from "trickMode" video tracks,
|
|
1449
|
-
* which are tracks specifically defined to mimic the visual aspect of a VCR's
|
|
1450
|
-
* fast forward/rewind feature, by only displaying a few video frames during
|
|
1451
|
-
* playback.
|
|
1452
|
-
*
|
|
1453
|
-
* This behavior is configurable through the second argument, by adding a
|
|
1454
|
-
* property named `preferTrickModeTracks` to that object.
|
|
1455
|
-
*
|
|
1456
|
-
* You can set that value to `true` to switch to trickMode video tracks when
|
|
1457
|
-
* available, and set it to `false` when you want to disable that logic.
|
|
1458
|
-
* Note that like any configuration given to `setPlaybackRate`, this setting
|
|
1459
|
-
* is persisted through all future contents played by the player.
|
|
1460
|
-
*
|
|
1461
|
-
* If you want to stop enabling trickMode tracks, you will have to call
|
|
1462
|
-
* `setPlaybackRate` again with `preferTrickModeTracks` set to `false`.
|
|
1463
|
-
*
|
|
1464
|
-
* You can know at any moment whether this behavior is enabled by calling
|
|
1465
|
-
* the `areTrickModeTracksEnabled` method. This will only means that the
|
|
1466
|
-
* RxPlayer will select in priority trickmode video tracks, not that the
|
|
1467
|
-
* currently chosen video tracks is a trickmode track (for example, some
|
|
1468
|
-
* contents may have no trickmode tracks available).
|
|
1469
|
-
*
|
|
1470
|
-
* If you want to know about the latter instead, you can call `getVideoTrack`
|
|
1471
|
-
* and/or listen to `videoTrackChange` events. The track returned may have an
|
|
1472
|
-
* `isTrickModeTrack` property set to `true`, indicating that it is a
|
|
1473
|
-
* trickmode track.
|
|
1474
|
-
*
|
|
1475
|
-
* Note that switching to or getting out of a trickmode video track may
|
|
1476
|
-
* lead to the player being a brief instant in a `"RELOADING"` state (notified
|
|
1477
|
-
* through `playerStateChange` events and the `getLoadedContentState` method).
|
|
1478
|
-
* When in that state, a black screen may be displayed and multiple RxPlayer
|
|
1479
|
-
* APIs will not be usable.
|
|
1480
|
-
*
|
|
1481
|
-
* @param {Number} rate
|
|
1482
|
-
* @param {Object} opts
|
|
1483
|
-
*/
|
|
1484
|
-
setPlaybackRate(
|
|
1485
|
-
rate : number,
|
|
1486
|
-
opts? : { preferTrickModeTracks? : boolean }
|
|
1487
|
-
) : void {
|
|
1488
|
-
if (rate !== this._priv_speed.getValue()) {
|
|
1489
|
-
this._priv_speed.setValue(rate);
|
|
1490
|
-
}
|
|
1491
|
-
|
|
1492
|
-
const preferTrickModeTracks = opts?.preferTrickModeTracks;
|
|
1493
|
-
if (typeof preferTrickModeTracks !== "boolean") {
|
|
1494
|
-
return;
|
|
1495
|
-
}
|
|
1496
|
-
this._priv_preferTrickModeTracks = preferTrickModeTracks;
|
|
1497
|
-
const trackChoiceManager = this._priv_contentInfos?.trackChoiceManager;
|
|
1498
|
-
if (!isNullOrUndefined(trackChoiceManager)) {
|
|
1499
|
-
if (preferTrickModeTracks && !trackChoiceManager.isTrickModeEnabled()) {
|
|
1500
|
-
trackChoiceManager.enableVideoTrickModeTracks();
|
|
1501
|
-
} else if (!preferTrickModeTracks && trackChoiceManager.isTrickModeEnabled()) {
|
|
1502
|
-
trackChoiceManager.disableVideoTrickModeTracks();
|
|
1503
|
-
}
|
|
1504
|
-
}
|
|
1505
|
-
}
|
|
1506
|
-
|
|
1507
|
-
/**
|
|
1508
|
-
* Returns all available bitrates for the current video Adaptation.
|
|
1509
|
-
* @returns {Array.<Number>}
|
|
1510
|
-
*/
|
|
1511
|
-
getAvailableVideoBitrates() : number[] {
|
|
1512
|
-
if (this._priv_contentInfos === null) {
|
|
1513
|
-
return [];
|
|
1514
|
-
}
|
|
1515
|
-
const { currentPeriod, activeAdaptations } = this._priv_contentInfos;
|
|
1516
|
-
if (currentPeriod === null || activeAdaptations === null) {
|
|
1517
|
-
return [];
|
|
1518
|
-
}
|
|
1519
|
-
const adaptations = activeAdaptations[currentPeriod.id];
|
|
1520
|
-
if (adaptations === undefined || isNullOrUndefined(adaptations.video)) {
|
|
1521
|
-
return [];
|
|
1522
|
-
}
|
|
1523
|
-
|
|
1524
|
-
return adaptations.video.getAvailableBitrates();
|
|
1525
|
-
}
|
|
1526
|
-
|
|
1527
|
-
/**
|
|
1528
|
-
* Returns all available bitrates for the current audio Adaptation.
|
|
1529
|
-
* @returns {Array.<Number>}
|
|
1530
|
-
*/
|
|
1531
|
-
getAvailableAudioBitrates() : number[] {
|
|
1532
|
-
if (this._priv_contentInfos === null) {
|
|
1533
|
-
return [];
|
|
1534
|
-
}
|
|
1535
|
-
const { currentPeriod, activeAdaptations } = this._priv_contentInfos;
|
|
1536
|
-
if (currentPeriod === null || activeAdaptations === null) {
|
|
1537
|
-
return [];
|
|
1538
|
-
}
|
|
1539
|
-
const adaptations = activeAdaptations[currentPeriod.id];
|
|
1540
|
-
if (adaptations === undefined || isNullOrUndefined(adaptations.audio)) {
|
|
1541
|
-
return [];
|
|
1542
|
-
}
|
|
1543
|
-
|
|
1544
|
-
return adaptations.audio.getAvailableBitrates();
|
|
1545
|
-
}
|
|
1546
|
-
|
|
1547
|
-
/**
|
|
1548
|
-
* Returns the manual audio bitrate set. -1 if in AUTO mode.
|
|
1549
|
-
* @returns {Number}
|
|
1550
|
-
*/
|
|
1551
|
-
getManualAudioBitrate() : number {
|
|
1552
|
-
return this._priv_bitrateInfos.manualBitrates.audio.getValue();
|
|
1553
|
-
}
|
|
1554
|
-
|
|
1555
|
-
/**
|
|
1556
|
-
* Returns the manual video bitrate set. -1 if in AUTO mode.
|
|
1557
|
-
* @returns {Number}
|
|
1558
|
-
*/
|
|
1559
|
-
getManualVideoBitrate() : number {
|
|
1560
|
-
return this._priv_bitrateInfos.manualBitrates.video.getValue();
|
|
1561
|
-
}
|
|
1562
|
-
|
|
1563
|
-
/**
|
|
1564
|
-
* Returns currently considered bitrate for video segments.
|
|
1565
|
-
* @returns {Number|undefined}
|
|
1566
|
-
*/
|
|
1567
|
-
getVideoBitrate() : number|undefined {
|
|
1568
|
-
const representations = this._priv_getCurrentRepresentations();
|
|
1569
|
-
if (representations === null || isNullOrUndefined(representations.video)) {
|
|
1570
|
-
return undefined;
|
|
1571
|
-
}
|
|
1572
|
-
return representations.video.bitrate;
|
|
1573
|
-
}
|
|
1574
|
-
|
|
1575
|
-
/**
|
|
1576
|
-
* Returns currently considered bitrate for audio segments.
|
|
1577
|
-
* @returns {Number|undefined}
|
|
1578
|
-
*/
|
|
1579
|
-
getAudioBitrate() : number|undefined {
|
|
1580
|
-
const representations = this._priv_getCurrentRepresentations();
|
|
1581
|
-
if (representations === null || isNullOrUndefined(representations.audio)) {
|
|
1582
|
-
return undefined;
|
|
1583
|
-
}
|
|
1584
|
-
return representations.audio.bitrate;
|
|
1585
|
-
}
|
|
1586
|
-
|
|
1587
|
-
/**
|
|
1588
|
-
* Returns minimum wanted video bitrate currently set.
|
|
1589
|
-
* @returns {Number}
|
|
1590
|
-
*/
|
|
1591
|
-
getMinVideoBitrate() : number {
|
|
1592
|
-
return this._priv_bitrateInfos.minAutoBitrates.video.getValue();
|
|
1593
|
-
}
|
|
1594
|
-
|
|
1595
|
-
/**
|
|
1596
|
-
* Returns minimum wanted audio bitrate currently set.
|
|
1597
|
-
* @returns {Number}
|
|
1598
|
-
*/
|
|
1599
|
-
getMinAudioBitrate() : number {
|
|
1600
|
-
return this._priv_bitrateInfos.minAutoBitrates.audio.getValue();
|
|
1601
|
-
}
|
|
1602
|
-
|
|
1603
|
-
/**
|
|
1604
|
-
* Returns maximum wanted video bitrate currently set.
|
|
1605
|
-
* @returns {Number}
|
|
1606
|
-
*/
|
|
1607
|
-
getMaxVideoBitrate() : number {
|
|
1608
|
-
return this._priv_bitrateInfos.maxAutoBitrates.video.getValue();
|
|
1609
|
-
}
|
|
1610
|
-
|
|
1611
|
-
/**
|
|
1612
|
-
* Returns maximum wanted audio bitrate currently set.
|
|
1613
|
-
* @returns {Number}
|
|
1614
|
-
*/
|
|
1615
|
-
getMaxAudioBitrate() : number {
|
|
1616
|
-
return this._priv_bitrateInfos.maxAutoBitrates.audio.getValue();
|
|
1617
|
-
}
|
|
1618
|
-
|
|
1619
|
-
/**
|
|
1620
|
-
* Play/Resume the current video.
|
|
1621
|
-
* @returns {Promise}
|
|
1622
|
-
*/
|
|
1623
|
-
play() : Promise<void> {
|
|
1624
|
-
if (this.videoElement === null) {
|
|
1625
|
-
throw new Error("Disposed player");
|
|
1626
|
-
}
|
|
1627
|
-
|
|
1628
|
-
const playPromise = this.videoElement.play();
|
|
1629
|
-
/* eslint-disable @typescript-eslint/unbound-method */
|
|
1630
|
-
if (isNullOrUndefined(playPromise) || typeof playPromise.catch !== "function") {
|
|
1631
|
-
/* eslint-enable @typescript-eslint/unbound-method */
|
|
1632
|
-
return Promise.resolve();
|
|
1633
|
-
}
|
|
1634
|
-
return playPromise.catch((error: Error) => {
|
|
1635
|
-
if (error.name === "NotAllowedError") {
|
|
1636
|
-
const warning = new MediaError("MEDIA_ERR_PLAY_NOT_ALLOWED",
|
|
1637
|
-
error.toString());
|
|
1638
|
-
this.trigger("warning", warning);
|
|
1639
|
-
}
|
|
1640
|
-
throw error;
|
|
1641
|
-
});
|
|
1642
|
-
}
|
|
1643
|
-
|
|
1644
|
-
/**
|
|
1645
|
-
* Pause the current video.
|
|
1646
|
-
*/
|
|
1647
|
-
pause() : void {
|
|
1648
|
-
if (this.videoElement === null) {
|
|
1649
|
-
throw new Error("Disposed player");
|
|
1650
|
-
}
|
|
1651
|
-
this.videoElement.pause();
|
|
1652
|
-
}
|
|
1653
|
-
|
|
1654
|
-
/**
|
|
1655
|
-
* Seek to a given absolute position.
|
|
1656
|
-
* @param {Number|Object} time
|
|
1657
|
-
* @returns {Number} - The time the player has seek to
|
|
1658
|
-
*/
|
|
1659
|
-
seekTo(
|
|
1660
|
-
time : number | { relative : number } | { position : number } |
|
|
1661
|
-
{ wallClockTime : number }
|
|
1662
|
-
) : number {
|
|
1663
|
-
if (this.videoElement === null) {
|
|
1664
|
-
throw new Error("Disposed player");
|
|
1665
|
-
}
|
|
1666
|
-
if (this._priv_contentInfos === null) {
|
|
1667
|
-
throw new Error("player: no content loaded");
|
|
1668
|
-
}
|
|
1669
|
-
|
|
1670
|
-
const { isDirectFile, manifest } = this._priv_contentInfos;
|
|
1671
|
-
if (!isDirectFile && manifest === null) {
|
|
1672
|
-
throw new Error("player: the content did not load yet");
|
|
1673
|
-
}
|
|
1674
|
-
|
|
1675
|
-
let positionWanted : number|undefined;
|
|
1676
|
-
|
|
1677
|
-
if (typeof time === "number") {
|
|
1678
|
-
positionWanted = time;
|
|
1679
|
-
} else if (typeof time === "object") {
|
|
1680
|
-
const timeObj : { time? : number;
|
|
1681
|
-
relative? : number;
|
|
1682
|
-
position? : number;
|
|
1683
|
-
wallClockTime? : number; } = time;
|
|
1684
|
-
const currentTs = this.videoElement.currentTime;
|
|
1685
|
-
if (!isNullOrUndefined(timeObj.relative)) {
|
|
1686
|
-
positionWanted = currentTs + timeObj.relative;
|
|
1687
|
-
} else if (!isNullOrUndefined(timeObj.position)) {
|
|
1688
|
-
positionWanted = timeObj.position;
|
|
1689
|
-
} else if (!isNullOrUndefined(timeObj.wallClockTime)) {
|
|
1690
|
-
if (manifest !== null) {
|
|
1691
|
-
positionWanted = timeObj.wallClockTime - (
|
|
1692
|
-
manifest.availabilityStartTime ?? 0
|
|
1693
|
-
);
|
|
1694
|
-
} else if (isDirectFile && this.videoElement !== null) {
|
|
1695
|
-
const startDate = getStartDate(this.videoElement);
|
|
1696
|
-
if (startDate !== undefined) {
|
|
1697
|
-
positionWanted = timeObj.wallClockTime - startDate;
|
|
1698
|
-
}
|
|
1699
|
-
}
|
|
1700
|
-
if (positionWanted === undefined) {
|
|
1701
|
-
positionWanted = timeObj.wallClockTime;
|
|
1702
|
-
}
|
|
1703
|
-
} else {
|
|
1704
|
-
throw new Error("invalid time object. You must set one of the " +
|
|
1705
|
-
"following properties: \"relative\", \"position\" or " +
|
|
1706
|
-
"\"wallClockTime\"");
|
|
1707
|
-
}
|
|
1708
|
-
}
|
|
1709
|
-
|
|
1710
|
-
if (positionWanted === undefined) {
|
|
1711
|
-
throw new Error("invalid time given");
|
|
1712
|
-
}
|
|
1713
|
-
log.info("API: API Seek to", positionWanted);
|
|
1714
|
-
this.videoElement.currentTime = positionWanted;
|
|
1715
|
-
return positionWanted;
|
|
1716
|
-
}
|
|
1717
|
-
|
|
1718
|
-
/**
|
|
1719
|
-
* Returns true if the media element is full screen.
|
|
1720
|
-
* @deprecated
|
|
1721
|
-
* @returns {Boolean}
|
|
1722
|
-
*/
|
|
1723
|
-
isFullscreen() : boolean {
|
|
1724
|
-
warnOnce("isFullscreen is deprecated." +
|
|
1725
|
-
" Fullscreen management should now be managed by the application");
|
|
1726
|
-
return isFullscreen();
|
|
1727
|
-
}
|
|
1728
|
-
|
|
1729
|
-
/**
|
|
1730
|
-
* Set/exit fullScreen.
|
|
1731
|
-
* @deprecated
|
|
1732
|
-
* @param {Boolean} [goFull=true] - if false, exit full screen.
|
|
1733
|
-
*/
|
|
1734
|
-
setFullscreen(goFull : boolean = true) : void {
|
|
1735
|
-
warnOnce("setFullscreen is deprecated." +
|
|
1736
|
-
" Fullscreen management should now be managed by the application");
|
|
1737
|
-
if (this.videoElement === null) {
|
|
1738
|
-
throw new Error("Disposed player");
|
|
1739
|
-
}
|
|
1740
|
-
|
|
1741
|
-
if (goFull) {
|
|
1742
|
-
requestFullscreen(this.videoElement);
|
|
1743
|
-
} else {
|
|
1744
|
-
exitFullscreen();
|
|
1745
|
-
}
|
|
1746
|
-
}
|
|
1747
|
-
|
|
1748
|
-
/**
|
|
1749
|
-
* Exit from full screen mode.
|
|
1750
|
-
* @deprecated
|
|
1751
|
-
*/
|
|
1752
|
-
exitFullscreen() : void {
|
|
1753
|
-
warnOnce("exitFullscreen is deprecated." +
|
|
1754
|
-
" Fullscreen management should now be managed by the application");
|
|
1755
|
-
exitFullscreen();
|
|
1756
|
-
}
|
|
1757
|
-
|
|
1758
|
-
/**
|
|
1759
|
-
* Returns the current player's audio volume on the media element.
|
|
1760
|
-
* From 0 (no audio) to 1 (maximum volume).
|
|
1761
|
-
* @returns {Number}
|
|
1762
|
-
*/
|
|
1763
|
-
getVolume() : number {
|
|
1764
|
-
if (this.videoElement === null) {
|
|
1765
|
-
throw new Error("Disposed player");
|
|
1766
|
-
}
|
|
1767
|
-
return this.videoElement.volume;
|
|
1768
|
-
}
|
|
1769
|
-
|
|
1770
|
-
/**
|
|
1771
|
-
* Set the player's audio volume. From 0 (no volume) to 1 (maximum volume).
|
|
1772
|
-
* @param {Number} volume
|
|
1773
|
-
*/
|
|
1774
|
-
setVolume(volume : number) : void {
|
|
1775
|
-
if (this.videoElement === null) {
|
|
1776
|
-
throw new Error("Disposed player");
|
|
1777
|
-
}
|
|
1778
|
-
|
|
1779
|
-
const videoElement = this.videoElement;
|
|
1780
|
-
if (volume !== videoElement.volume) {
|
|
1781
|
-
videoElement.volume = volume;
|
|
1782
|
-
this.trigger("volumeChange", volume);
|
|
1783
|
-
}
|
|
1784
|
-
}
|
|
1785
|
-
|
|
1786
|
-
/**
|
|
1787
|
-
* Returns true if the volume is set to 0. false otherwise.
|
|
1788
|
-
* @returns {Boolean}
|
|
1789
|
-
*/
|
|
1790
|
-
isMute() : boolean {
|
|
1791
|
-
return this.getVolume() === 0;
|
|
1792
|
-
}
|
|
1793
|
-
|
|
1794
|
-
/**
|
|
1795
|
-
* Set the volume to 0 and save current one for when unmuted.
|
|
1796
|
-
*/
|
|
1797
|
-
mute() : void {
|
|
1798
|
-
this._priv_mutedMemory = this.getVolume();
|
|
1799
|
-
this.setVolume(0);
|
|
1800
|
-
}
|
|
1801
|
-
|
|
1802
|
-
/**
|
|
1803
|
-
* Set the volume back to when it was when mute was last called.
|
|
1804
|
-
* If the volume was set to 0, set a default volume instead (see config).
|
|
1805
|
-
*/
|
|
1806
|
-
unMute() : void {
|
|
1807
|
-
const { DEFAULT_UNMUTED_VOLUME } = config.getCurrent();
|
|
1808
|
-
const vol = this.getVolume();
|
|
1809
|
-
if (vol === 0) {
|
|
1810
|
-
this.setVolume(this._priv_mutedMemory === 0 ? DEFAULT_UNMUTED_VOLUME :
|
|
1811
|
-
this._priv_mutedMemory);
|
|
1812
|
-
}
|
|
1813
|
-
}
|
|
1814
|
-
|
|
1815
|
-
/**
|
|
1816
|
-
* Force the video bitrate to a given value. Act as a ceil.
|
|
1817
|
-
* -1 to set it on AUTO Mode
|
|
1818
|
-
* @param {Number} btr
|
|
1819
|
-
*/
|
|
1820
|
-
setVideoBitrate(btr : number) : void {
|
|
1821
|
-
this._priv_bitrateInfos.manualBitrates.video.setValue(btr);
|
|
1822
|
-
}
|
|
1823
|
-
|
|
1824
|
-
/**
|
|
1825
|
-
* Force the audio bitrate to a given value. Act as a ceil.
|
|
1826
|
-
* -1 to set it on AUTO Mode
|
|
1827
|
-
* @param {Number} btr
|
|
1828
|
-
*/
|
|
1829
|
-
setAudioBitrate(btr : number) : void {
|
|
1830
|
-
this._priv_bitrateInfos.manualBitrates.audio.setValue(btr);
|
|
1831
|
-
}
|
|
1832
|
-
|
|
1833
|
-
/**
|
|
1834
|
-
* Update the minimum video bitrate the user can switch to.
|
|
1835
|
-
* @param {Number} btr
|
|
1836
|
-
*/
|
|
1837
|
-
setMinVideoBitrate(btr : number) : void {
|
|
1838
|
-
const maxVideoBitrate = this._priv_bitrateInfos.maxAutoBitrates.video.getValue();
|
|
1839
|
-
if (btr > maxVideoBitrate) {
|
|
1840
|
-
throw new Error("Invalid minimum video bitrate given. " +
|
|
1841
|
-
`Its value, "${btr}" is superior the current maximum ` +
|
|
1842
|
-
`video birate, "${maxVideoBitrate}".`);
|
|
1843
|
-
}
|
|
1844
|
-
this._priv_bitrateInfos.minAutoBitrates.video.setValue(btr);
|
|
1845
|
-
}
|
|
1846
|
-
|
|
1847
|
-
/**
|
|
1848
|
-
* Update the minimum audio bitrate the user can switch to.
|
|
1849
|
-
* @param {Number} btr
|
|
1850
|
-
*/
|
|
1851
|
-
setMinAudioBitrate(btr : number) : void {
|
|
1852
|
-
const maxAudioBitrate = this._priv_bitrateInfos.maxAutoBitrates.audio.getValue();
|
|
1853
|
-
if (btr > maxAudioBitrate) {
|
|
1854
|
-
throw new Error("Invalid minimum audio bitrate given. " +
|
|
1855
|
-
`Its value, "${btr}" is superior the current maximum ` +
|
|
1856
|
-
`audio birate, "${maxAudioBitrate}".`);
|
|
1857
|
-
}
|
|
1858
|
-
this._priv_bitrateInfos.minAutoBitrates.audio.setValue(btr);
|
|
1859
|
-
}
|
|
1860
|
-
|
|
1861
|
-
/**
|
|
1862
|
-
* Update the maximum video bitrate the user can switch to.
|
|
1863
|
-
* @param {Number} btr
|
|
1864
|
-
*/
|
|
1865
|
-
setMaxVideoBitrate(btr : number) : void {
|
|
1866
|
-
const minVideoBitrate = this._priv_bitrateInfos.minAutoBitrates.video.getValue();
|
|
1867
|
-
if (btr < minVideoBitrate) {
|
|
1868
|
-
throw new Error("Invalid maximum video bitrate given. " +
|
|
1869
|
-
`Its value, "${btr}" is inferior the current minimum ` +
|
|
1870
|
-
`video birate, "${minVideoBitrate}".`);
|
|
1871
|
-
}
|
|
1872
|
-
this._priv_bitrateInfos.maxAutoBitrates.video.setValue(btr);
|
|
1873
|
-
}
|
|
1874
|
-
|
|
1875
|
-
/**
|
|
1876
|
-
* Update the maximum audio bitrate the user can switch to.
|
|
1877
|
-
* @param {Number} btr
|
|
1878
|
-
*/
|
|
1879
|
-
setMaxAudioBitrate(btr : number) : void {
|
|
1880
|
-
const minAudioBitrate = this._priv_bitrateInfos.minAutoBitrates.audio.getValue();
|
|
1881
|
-
if (btr < minAudioBitrate) {
|
|
1882
|
-
throw new Error("Invalid maximum audio bitrate given. " +
|
|
1883
|
-
`Its value, "${btr}" is inferior the current minimum ` +
|
|
1884
|
-
`audio birate, "${minAudioBitrate}".`);
|
|
1885
|
-
}
|
|
1886
|
-
this._priv_bitrateInfos.maxAutoBitrates.audio.setValue(btr);
|
|
1887
|
-
}
|
|
1888
|
-
|
|
1889
|
-
/**
|
|
1890
|
-
* Set the max buffer size for the buffer behind the current position.
|
|
1891
|
-
* Every buffer data before will be removed.
|
|
1892
|
-
* @param {Number} depthInSeconds
|
|
1893
|
-
*/
|
|
1894
|
-
setMaxBufferBehind(depthInSeconds : number) : void {
|
|
1895
|
-
this._priv_bufferOptions.maxBufferBehind.setValue(depthInSeconds);
|
|
1896
|
-
}
|
|
1897
|
-
|
|
1898
|
-
/**
|
|
1899
|
-
* Set the max buffer size for the buffer behind the current position.
|
|
1900
|
-
* Every buffer data before will be removed.
|
|
1901
|
-
* @param {Number} depthInSeconds
|
|
1902
|
-
*/
|
|
1903
|
-
setMaxBufferAhead(depthInSeconds : number) : void {
|
|
1904
|
-
this._priv_bufferOptions.maxBufferAhead.setValue(depthInSeconds);
|
|
1905
|
-
}
|
|
1906
|
-
|
|
1907
|
-
/**
|
|
1908
|
-
* Set the max buffer size for the buffer ahead of the current position.
|
|
1909
|
-
* The player will stop downloading chunks when this size is reached.
|
|
1910
|
-
* @param {Number} sizeInSeconds
|
|
1911
|
-
*/
|
|
1912
|
-
setWantedBufferAhead(sizeInSeconds : number) : void {
|
|
1913
|
-
this._priv_bufferOptions.wantedBufferAhead.setValue(sizeInSeconds);
|
|
1914
|
-
}
|
|
1915
|
-
|
|
1916
|
-
/**
|
|
1917
|
-
* Set the max buffer size the buffer should take in memory
|
|
1918
|
-
* The player . will stop downloading chunks when this size is reached.
|
|
1919
|
-
* @param {Number} sizeInKBytes
|
|
1920
|
-
*/
|
|
1921
|
-
setMaxVideoBufferSize(sizeInKBytes : number) : void {
|
|
1922
|
-
this._priv_bufferOptions.maxVideoBufferSize.setValue(sizeInKBytes);
|
|
1923
|
-
}
|
|
1924
|
-
|
|
1925
|
-
/**
|
|
1926
|
-
* Returns the max buffer size for the buffer behind the current position.
|
|
1927
|
-
* @returns {Number}
|
|
1928
|
-
*/
|
|
1929
|
-
getMaxBufferBehind() : number {
|
|
1930
|
-
return this._priv_bufferOptions.maxBufferBehind.getValue();
|
|
1931
|
-
}
|
|
1932
|
-
|
|
1933
|
-
/**
|
|
1934
|
-
* Returns the max buffer size for the buffer behind the current position.
|
|
1935
|
-
* @returns {Number}
|
|
1936
|
-
*/
|
|
1937
|
-
getMaxBufferAhead() : number {
|
|
1938
|
-
return this._priv_bufferOptions.maxBufferAhead.getValue();
|
|
1939
|
-
}
|
|
1940
|
-
|
|
1941
|
-
/**
|
|
1942
|
-
* Returns the max buffer size for the buffer ahead of the current position.
|
|
1943
|
-
* @returns {Number}
|
|
1944
|
-
*/
|
|
1945
|
-
getWantedBufferAhead() : number {
|
|
1946
|
-
return this._priv_bufferOptions.wantedBufferAhead.getValue();
|
|
1947
|
-
}
|
|
1948
|
-
|
|
1949
|
-
/**
|
|
1950
|
-
* Returns the max buffer memory size for the buffer in kilobytes
|
|
1951
|
-
* @returns {Number}
|
|
1952
|
-
*/
|
|
1953
|
-
getMaxVideoBufferSize() : number {
|
|
1954
|
-
return this._priv_bufferOptions.maxVideoBufferSize.getValue();
|
|
1955
|
-
}
|
|
1956
|
-
|
|
1957
|
-
/**
|
|
1958
|
-
* Returns type of current keysystem (e.g. playready, widevine) if the content
|
|
1959
|
-
* is encrypted. null otherwise.
|
|
1960
|
-
* @deprecated
|
|
1961
|
-
* @returns {string|null}
|
|
1962
|
-
*/
|
|
1963
|
-
getCurrentKeySystem() : string|null {
|
|
1964
|
-
warnOnce("`getCurrentKeySystem` is deprecated." +
|
|
1965
|
-
"Please use the `getKeySystemConfiguration` method instead.");
|
|
1966
|
-
if (this.videoElement === null) {
|
|
1967
|
-
throw new Error("Disposed player");
|
|
1968
|
-
}
|
|
1969
|
-
return getCurrentKeySystem(this.videoElement);
|
|
1970
|
-
}
|
|
1971
|
-
|
|
1972
|
-
/**
|
|
1973
|
-
* Returns both the name of the key system (e.g. `"com.widevine.alpha"`) and
|
|
1974
|
-
* the `MediaKeySystemConfiguration` currently associated to the
|
|
1975
|
-
* HTMLMediaElement linked to the RxPlayer.
|
|
1976
|
-
*
|
|
1977
|
-
* Returns `null` if no such capabilities is associated or if unknown.
|
|
1978
|
-
* @returns {Object|null}
|
|
1979
|
-
*/
|
|
1980
|
-
getKeySystemConfiguration() : IKeySystemConfigurationOutput | null {
|
|
1981
|
-
if (this.videoElement === null) {
|
|
1982
|
-
throw new Error("Disposed player");
|
|
1983
|
-
}
|
|
1984
|
-
const values = getKeySystemConfiguration(this.videoElement);
|
|
1985
|
-
if (values === null) {
|
|
1986
|
-
return null;
|
|
1987
|
-
}
|
|
1988
|
-
return { keySystem: values[0], configuration: values[1] };
|
|
1989
|
-
}
|
|
1990
|
-
|
|
1991
|
-
/**
|
|
1992
|
-
* Returns every available audio tracks for the current Period.
|
|
1993
|
-
* @returns {Array.<Object>|null}
|
|
1994
|
-
*/
|
|
1995
|
-
getAvailableAudioTracks() : IAvailableAudioTrack[] {
|
|
1996
|
-
if (this._priv_contentInfos === null) {
|
|
1997
|
-
return [];
|
|
1998
|
-
}
|
|
1999
|
-
const { currentPeriod,
|
|
2000
|
-
isDirectFile,
|
|
2001
|
-
trackChoiceManager,
|
|
2002
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2003
|
-
if (isDirectFile) {
|
|
2004
|
-
return mediaElementTrackChoiceManager?.getAvailableAudioTracks() ?? [];
|
|
2005
|
-
}
|
|
2006
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2007
|
-
return [];
|
|
2008
|
-
}
|
|
2009
|
-
return trackChoiceManager.getAvailableAudioTracks(currentPeriod);
|
|
2010
|
-
}
|
|
2011
|
-
|
|
2012
|
-
/**
|
|
2013
|
-
* Returns every available text tracks for the current Period.
|
|
2014
|
-
* @returns {Array.<Object>|null}
|
|
2015
|
-
*/
|
|
2016
|
-
getAvailableTextTracks() : IAvailableTextTrack[] {
|
|
2017
|
-
if (this._priv_contentInfos === null) {
|
|
2018
|
-
return [];
|
|
2019
|
-
}
|
|
2020
|
-
const { currentPeriod,
|
|
2021
|
-
isDirectFile,
|
|
2022
|
-
trackChoiceManager,
|
|
2023
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2024
|
-
if (isDirectFile) {
|
|
2025
|
-
return mediaElementTrackChoiceManager?.getAvailableTextTracks() ?? [];
|
|
2026
|
-
}
|
|
2027
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2028
|
-
return [];
|
|
2029
|
-
}
|
|
2030
|
-
return trackChoiceManager.getAvailableTextTracks(currentPeriod);
|
|
2031
|
-
}
|
|
2032
|
-
|
|
2033
|
-
/**
|
|
2034
|
-
* Returns every available video tracks for the current Period.
|
|
2035
|
-
* @returns {Array.<Object>|null}
|
|
2036
|
-
*/
|
|
2037
|
-
getAvailableVideoTracks() : IAvailableVideoTrack[] {
|
|
2038
|
-
if (this._priv_contentInfos === null) {
|
|
2039
|
-
return [];
|
|
2040
|
-
}
|
|
2041
|
-
const { currentPeriod,
|
|
2042
|
-
isDirectFile,
|
|
2043
|
-
trackChoiceManager,
|
|
2044
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2045
|
-
if (isDirectFile) {
|
|
2046
|
-
return mediaElementTrackChoiceManager?.getAvailableVideoTracks() ?? [];
|
|
2047
|
-
}
|
|
2048
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2049
|
-
return [];
|
|
2050
|
-
}
|
|
2051
|
-
return trackChoiceManager.getAvailableVideoTracks(currentPeriod);
|
|
2052
|
-
}
|
|
2053
|
-
|
|
2054
|
-
/**
|
|
2055
|
-
* Returns currently chosen audio language for the current Period.
|
|
2056
|
-
* @returns {string}
|
|
2057
|
-
*/
|
|
2058
|
-
getAudioTrack() : IAudioTrack|null|undefined {
|
|
2059
|
-
if (this._priv_contentInfos === null) {
|
|
2060
|
-
return undefined;
|
|
2061
|
-
}
|
|
2062
|
-
const { currentPeriod,
|
|
2063
|
-
isDirectFile,
|
|
2064
|
-
trackChoiceManager,
|
|
2065
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2066
|
-
if (isDirectFile) {
|
|
2067
|
-
if (mediaElementTrackChoiceManager === null) {
|
|
2068
|
-
return undefined;
|
|
2069
|
-
}
|
|
2070
|
-
return mediaElementTrackChoiceManager.getChosenAudioTrack();
|
|
2071
|
-
}
|
|
2072
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2073
|
-
return undefined;
|
|
2074
|
-
}
|
|
2075
|
-
return trackChoiceManager.getChosenAudioTrack(currentPeriod);
|
|
2076
|
-
}
|
|
2077
|
-
|
|
2078
|
-
/**
|
|
2079
|
-
* Returns currently chosen subtitle for the current Period.
|
|
2080
|
-
* @returns {string}
|
|
2081
|
-
*/
|
|
2082
|
-
getTextTrack() : ITextTrack|null|undefined {
|
|
2083
|
-
if (this._priv_contentInfos === null) {
|
|
2084
|
-
return undefined;
|
|
2085
|
-
}
|
|
2086
|
-
const { currentPeriod,
|
|
2087
|
-
isDirectFile,
|
|
2088
|
-
trackChoiceManager,
|
|
2089
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2090
|
-
if (isDirectFile) {
|
|
2091
|
-
if (mediaElementTrackChoiceManager === null) {
|
|
2092
|
-
return undefined;
|
|
2093
|
-
}
|
|
2094
|
-
return mediaElementTrackChoiceManager.getChosenTextTrack();
|
|
2095
|
-
}
|
|
2096
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2097
|
-
return undefined;
|
|
2098
|
-
}
|
|
2099
|
-
return trackChoiceManager.getChosenTextTrack(currentPeriod);
|
|
2100
|
-
}
|
|
2101
|
-
|
|
2102
|
-
/**
|
|
2103
|
-
* Returns currently chosen video track for the current Period.
|
|
2104
|
-
* @returns {string}
|
|
2105
|
-
*/
|
|
2106
|
-
getVideoTrack() : IVideoTrack|null|undefined {
|
|
2107
|
-
if (this._priv_contentInfos === null) {
|
|
2108
|
-
return undefined;
|
|
2109
|
-
}
|
|
2110
|
-
const { currentPeriod,
|
|
2111
|
-
isDirectFile,
|
|
2112
|
-
trackChoiceManager,
|
|
2113
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2114
|
-
if (isDirectFile) {
|
|
2115
|
-
if (mediaElementTrackChoiceManager === null) {
|
|
2116
|
-
return undefined;
|
|
2117
|
-
}
|
|
2118
|
-
return mediaElementTrackChoiceManager.getChosenVideoTrack();
|
|
2119
|
-
}
|
|
2120
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2121
|
-
return undefined;
|
|
2122
|
-
}
|
|
2123
|
-
return trackChoiceManager.getChosenVideoTrack(currentPeriod);
|
|
2124
|
-
}
|
|
2125
|
-
|
|
2126
|
-
/**
|
|
2127
|
-
* Update the audio language for the current Period.
|
|
2128
|
-
* @param {string} audioId
|
|
2129
|
-
* @throws Error - the current content has no TrackChoiceManager.
|
|
2130
|
-
* @throws Error - the given id is linked to no audio track.
|
|
2131
|
-
*/
|
|
2132
|
-
setAudioTrack(audioId : string) : void {
|
|
2133
|
-
if (this._priv_contentInfos === null) {
|
|
2134
|
-
throw new Error("No content loaded");
|
|
2135
|
-
}
|
|
2136
|
-
const { currentPeriod,
|
|
2137
|
-
isDirectFile,
|
|
2138
|
-
trackChoiceManager,
|
|
2139
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2140
|
-
if (isDirectFile) {
|
|
2141
|
-
try {
|
|
2142
|
-
mediaElementTrackChoiceManager?.setAudioTrackById(audioId);
|
|
2143
|
-
return;
|
|
2144
|
-
} catch (e) {
|
|
2145
|
-
throw new Error("player: unknown audio track");
|
|
2146
|
-
}
|
|
2147
|
-
}
|
|
2148
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2149
|
-
throw new Error("No compatible content launched.");
|
|
2150
|
-
}
|
|
2151
|
-
try {
|
|
2152
|
-
trackChoiceManager.setAudioTrackByID(currentPeriod, audioId);
|
|
2153
|
-
}
|
|
2154
|
-
catch (e) {
|
|
2155
|
-
throw new Error("player: unknown audio track");
|
|
2156
|
-
}
|
|
2157
|
-
}
|
|
2158
|
-
|
|
2159
|
-
/**
|
|
2160
|
-
* Update the text language for the current Period.
|
|
2161
|
-
* @param {string} sub
|
|
2162
|
-
* @throws Error - the current content has no TrackChoiceManager.
|
|
2163
|
-
* @throws Error - the given id is linked to no text track.
|
|
2164
|
-
*/
|
|
2165
|
-
setTextTrack(textId : string) : void {
|
|
2166
|
-
if (this._priv_contentInfos === null) {
|
|
2167
|
-
throw new Error("No content loaded");
|
|
2168
|
-
}
|
|
2169
|
-
const { currentPeriod,
|
|
2170
|
-
isDirectFile,
|
|
2171
|
-
trackChoiceManager,
|
|
2172
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2173
|
-
if (isDirectFile) {
|
|
2174
|
-
try {
|
|
2175
|
-
mediaElementTrackChoiceManager?.setTextTrackById(textId);
|
|
2176
|
-
return;
|
|
2177
|
-
} catch (e) {
|
|
2178
|
-
throw new Error("player: unknown text track");
|
|
2179
|
-
}
|
|
2180
|
-
}
|
|
2181
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2182
|
-
throw new Error("No compatible content launched.");
|
|
2183
|
-
}
|
|
2184
|
-
try {
|
|
2185
|
-
trackChoiceManager.setTextTrackByID(currentPeriod, textId);
|
|
2186
|
-
}
|
|
2187
|
-
catch (e) {
|
|
2188
|
-
throw new Error("player: unknown text track");
|
|
2189
|
-
}
|
|
2190
|
-
}
|
|
2191
|
-
|
|
2192
|
-
/**
|
|
2193
|
-
* Disable subtitles for the current content.
|
|
2194
|
-
*/
|
|
2195
|
-
disableTextTrack() : void {
|
|
2196
|
-
if (this._priv_contentInfos === null) {
|
|
2197
|
-
return;
|
|
2198
|
-
}
|
|
2199
|
-
const { currentPeriod,
|
|
2200
|
-
isDirectFile,
|
|
2201
|
-
trackChoiceManager,
|
|
2202
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2203
|
-
if (isDirectFile) {
|
|
2204
|
-
mediaElementTrackChoiceManager?.disableTextTrack();
|
|
2205
|
-
return;
|
|
2206
|
-
}
|
|
2207
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2208
|
-
return;
|
|
2209
|
-
}
|
|
2210
|
-
return trackChoiceManager.disableTextTrack(currentPeriod);
|
|
2211
|
-
}
|
|
2212
|
-
|
|
2213
|
-
/**
|
|
2214
|
-
* Update the video track for the current Period.
|
|
2215
|
-
* @param {string} videoId
|
|
2216
|
-
* @throws Error - the current content has no TrackChoiceManager.
|
|
2217
|
-
* @throws Error - the given id is linked to no video track.
|
|
2218
|
-
*/
|
|
2219
|
-
setVideoTrack(videoId : string) : void {
|
|
2220
|
-
if (this._priv_contentInfos === null) {
|
|
2221
|
-
throw new Error("No content loaded");
|
|
2222
|
-
}
|
|
2223
|
-
const { currentPeriod,
|
|
2224
|
-
isDirectFile,
|
|
2225
|
-
trackChoiceManager,
|
|
2226
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2227
|
-
if (isDirectFile) {
|
|
2228
|
-
try {
|
|
2229
|
-
mediaElementTrackChoiceManager?.setVideoTrackById(videoId);
|
|
2230
|
-
return;
|
|
2231
|
-
} catch (e) {
|
|
2232
|
-
throw new Error("player: unknown video track");
|
|
2233
|
-
}
|
|
2234
|
-
}
|
|
2235
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2236
|
-
throw new Error("No compatible content launched.");
|
|
2237
|
-
}
|
|
2238
|
-
try {
|
|
2239
|
-
trackChoiceManager.setVideoTrackByID(currentPeriod, videoId);
|
|
2240
|
-
}
|
|
2241
|
-
catch (e) {
|
|
2242
|
-
throw new Error("player: unknown video track");
|
|
2243
|
-
}
|
|
2244
|
-
}
|
|
2245
|
-
|
|
2246
|
-
/**
|
|
2247
|
-
* Disable video track for the current content.
|
|
2248
|
-
*/
|
|
2249
|
-
disableVideoTrack() : void {
|
|
2250
|
-
if (this._priv_contentInfos === null) {
|
|
2251
|
-
return;
|
|
2252
|
-
}
|
|
2253
|
-
const { currentPeriod,
|
|
2254
|
-
isDirectFile,
|
|
2255
|
-
trackChoiceManager,
|
|
2256
|
-
mediaElementTrackChoiceManager } = this._priv_contentInfos;
|
|
2257
|
-
if (isDirectFile && mediaElementTrackChoiceManager !== null) {
|
|
2258
|
-
return mediaElementTrackChoiceManager.disableVideoTrack();
|
|
2259
|
-
}
|
|
2260
|
-
if (trackChoiceManager === null || currentPeriod === null) {
|
|
2261
|
-
return;
|
|
2262
|
-
}
|
|
2263
|
-
return trackChoiceManager.disableVideoTrack(currentPeriod);
|
|
2264
|
-
}
|
|
2265
|
-
|
|
2266
|
-
/**
|
|
2267
|
-
* Returns the current list of preferred audio tracks, in preference order.
|
|
2268
|
-
* @returns {Array.<Object>}
|
|
2269
|
-
*/
|
|
2270
|
-
getPreferredAudioTracks() : IAudioTrackPreference[] {
|
|
2271
|
-
return this._priv_preferredAudioTracks;
|
|
2272
|
-
}
|
|
2273
|
-
|
|
2274
|
-
/**
|
|
2275
|
-
* Returns the current list of preferred text tracks, in preference order.
|
|
2276
|
-
* @returns {Array.<Object>}
|
|
2277
|
-
*/
|
|
2278
|
-
getPreferredTextTracks() : ITextTrackPreference[] {
|
|
2279
|
-
return this._priv_preferredTextTracks;
|
|
2280
|
-
}
|
|
2281
|
-
|
|
2282
|
-
/**
|
|
2283
|
-
* Returns the current list of preferred text tracks, in preference order.
|
|
2284
|
-
* @returns {Array.<Object>}
|
|
2285
|
-
*/
|
|
2286
|
-
getPreferredVideoTracks() : IVideoTrackPreference[] {
|
|
2287
|
-
return this._priv_preferredVideoTracks;
|
|
2288
|
-
}
|
|
2289
|
-
|
|
2290
|
-
/**
|
|
2291
|
-
* Set the list of preferred audio tracks, in preference order.
|
|
2292
|
-
* @param {Array.<Object>} tracks
|
|
2293
|
-
* @param {boolean} shouldApply - `true` if those preferences should be
|
|
2294
|
-
* applied on the currently loaded Period. `false` if it should only
|
|
2295
|
-
* be applied to new content.
|
|
2296
|
-
*/
|
|
2297
|
-
setPreferredAudioTracks(
|
|
2298
|
-
tracks : IAudioTrackPreference[],
|
|
2299
|
-
shouldApply : boolean = false
|
|
2300
|
-
) : void {
|
|
2301
|
-
if (!Array.isArray(tracks)) {
|
|
2302
|
-
throw new Error("Invalid `setPreferredAudioTracks` argument. " +
|
|
2303
|
-
"Should have been an Array.");
|
|
2304
|
-
}
|
|
2305
|
-
this._priv_preferredAudioTracks = tracks;
|
|
2306
|
-
const contentInfos = this._priv_contentInfos;
|
|
2307
|
-
if (!isNullOrUndefined(contentInfos?.trackChoiceManager)) {
|
|
2308
|
-
contentInfos?.trackChoiceManager.setPreferredAudioTracks(tracks, shouldApply);
|
|
2309
|
-
} else if (!isNullOrUndefined(contentInfos?.mediaElementTrackChoiceManager)) {
|
|
2310
|
-
contentInfos?.mediaElementTrackChoiceManager.setPreferredAudioTracks(tracks,
|
|
2311
|
-
shouldApply);
|
|
2312
|
-
}
|
|
2313
|
-
}
|
|
2314
|
-
|
|
2315
|
-
/**
|
|
2316
|
-
* Set the list of preferred text tracks, in preference order.
|
|
2317
|
-
* @param {Array.<Object>} tracks
|
|
2318
|
-
* @param {boolean} shouldApply - `true` if those preferences should be
|
|
2319
|
-
* applied on the currently loaded Periods. `false` if it should only
|
|
2320
|
-
* be applied to new content.
|
|
2321
|
-
*/
|
|
2322
|
-
setPreferredTextTracks(
|
|
2323
|
-
tracks : ITextTrackPreference[],
|
|
2324
|
-
shouldApply : boolean = false
|
|
2325
|
-
) : void {
|
|
2326
|
-
if (!Array.isArray(tracks)) {
|
|
2327
|
-
throw new Error("Invalid `setPreferredTextTracks` argument. " +
|
|
2328
|
-
"Should have been an Array.");
|
|
2329
|
-
}
|
|
2330
|
-
this._priv_preferredTextTracks = tracks;
|
|
2331
|
-
const contentInfos = this._priv_contentInfos;
|
|
2332
|
-
if (!isNullOrUndefined(contentInfos?.trackChoiceManager)) {
|
|
2333
|
-
contentInfos?.trackChoiceManager.setPreferredTextTracks(tracks, shouldApply);
|
|
2334
|
-
} else if (!isNullOrUndefined(contentInfos?.mediaElementTrackChoiceManager)) {
|
|
2335
|
-
contentInfos?.mediaElementTrackChoiceManager.setPreferredTextTracks(tracks,
|
|
2336
|
-
shouldApply);
|
|
2337
|
-
}
|
|
2338
|
-
}
|
|
2339
|
-
|
|
2340
|
-
/**
|
|
2341
|
-
* Set the list of preferred text tracks, in preference order.
|
|
2342
|
-
* @param {Array.<Object>} tracks
|
|
2343
|
-
* @param {boolean} shouldApply - `true` if those preferences should be
|
|
2344
|
-
* applied on the currently loaded Period. `false` if it should only
|
|
2345
|
-
* be applied to new content.
|
|
2346
|
-
*/
|
|
2347
|
-
setPreferredVideoTracks(
|
|
2348
|
-
tracks : IVideoTrackPreference[],
|
|
2349
|
-
shouldApply : boolean = false
|
|
2350
|
-
) : void {
|
|
2351
|
-
if (!Array.isArray(tracks)) {
|
|
2352
|
-
throw new Error("Invalid `setPreferredVideoTracks` argument. " +
|
|
2353
|
-
"Should have been an Array.");
|
|
2354
|
-
}
|
|
2355
|
-
this._priv_preferredVideoTracks = tracks;
|
|
2356
|
-
const contentInfos = this._priv_contentInfos;
|
|
2357
|
-
if (!isNullOrUndefined(contentInfos?.trackChoiceManager)) {
|
|
2358
|
-
contentInfos?.trackChoiceManager.setPreferredVideoTracks(tracks, shouldApply);
|
|
2359
|
-
} else if (!isNullOrUndefined(contentInfos?.mediaElementTrackChoiceManager)) {
|
|
2360
|
-
contentInfos?.mediaElementTrackChoiceManager.setPreferredVideoTracks(tracks,
|
|
2361
|
-
shouldApply);
|
|
2362
|
-
}
|
|
2363
|
-
}
|
|
2364
|
-
|
|
2365
|
-
|
|
2366
|
-
/**
|
|
2367
|
-
* @returns {Array.<Object>|null}
|
|
2368
|
-
* @deprecated
|
|
2369
|
-
*/
|
|
2370
|
-
getImageTrackData() : IBifThumbnail[] | null {
|
|
2371
|
-
warnOnce("`getImageTrackData` is deprecated." +
|
|
2372
|
-
"Please use the `parseBifThumbnails` tool instead.");
|
|
2373
|
-
if (this._priv_contentInfos === null) {
|
|
2374
|
-
return null;
|
|
2375
|
-
}
|
|
2376
|
-
/* eslint-disable import/no-deprecated */
|
|
2377
|
-
return this._priv_contentInfos.thumbnails;
|
|
2378
|
-
/* eslint-enable import/no-deprecated */
|
|
2379
|
-
}
|
|
2380
|
-
|
|
2381
|
-
/**
|
|
2382
|
-
* Get minimum seek-able position.
|
|
2383
|
-
* @returns {number}
|
|
2384
|
-
*/
|
|
2385
|
-
getMinimumPosition() : number|null {
|
|
2386
|
-
if (this._priv_contentInfos === null) {
|
|
2387
|
-
return null;
|
|
2388
|
-
}
|
|
2389
|
-
|
|
2390
|
-
if (this._priv_contentInfos.isDirectFile) {
|
|
2391
|
-
return 0;
|
|
2392
|
-
}
|
|
2393
|
-
|
|
2394
|
-
const { manifest } = this._priv_contentInfos;
|
|
2395
|
-
if (manifest !== null) {
|
|
2396
|
-
return manifest.getMinimumSafePosition();
|
|
2397
|
-
}
|
|
2398
|
-
return null;
|
|
2399
|
-
}
|
|
2400
|
-
|
|
2401
|
-
/**
|
|
2402
|
-
* Returns the current position for live contents.
|
|
2403
|
-
*
|
|
2404
|
-
* Returns `null` if no content is loaded or if the current loaded content is
|
|
2405
|
-
* not considered as a live content.
|
|
2406
|
-
* Returns `undefined` if that live position is currently unknown.
|
|
2407
|
-
* @returns {number}
|
|
2408
|
-
*/
|
|
2409
|
-
getLivePosition() : number | undefined |null {
|
|
2410
|
-
if (this._priv_contentInfos === null) {
|
|
2411
|
-
return null;
|
|
2412
|
-
}
|
|
2413
|
-
|
|
2414
|
-
const { isDirectFile, manifest } = this._priv_contentInfos;
|
|
2415
|
-
if (isDirectFile) {
|
|
2416
|
-
return undefined;
|
|
2417
|
-
}
|
|
2418
|
-
if (manifest?.isLive !== true) {
|
|
2419
|
-
return null;
|
|
2420
|
-
}
|
|
2421
|
-
return manifest.getLivePosition();
|
|
2422
|
-
}
|
|
2423
|
-
|
|
2424
|
-
/**
|
|
2425
|
-
* Get maximum seek-able position.
|
|
2426
|
-
* @returns {number}
|
|
2427
|
-
*/
|
|
2428
|
-
getMaximumPosition() : number|null {
|
|
2429
|
-
if (this._priv_contentInfos === null) {
|
|
2430
|
-
return null;
|
|
2431
|
-
}
|
|
2432
|
-
|
|
2433
|
-
const { isDirectFile, manifest } = this._priv_contentInfos;
|
|
2434
|
-
|
|
2435
|
-
if (isDirectFile) {
|
|
2436
|
-
if (this.videoElement === null) {
|
|
2437
|
-
throw new Error("Disposed player");
|
|
2438
|
-
}
|
|
2439
|
-
return this.videoElement.duration;
|
|
2440
|
-
}
|
|
2441
|
-
|
|
2442
|
-
if (manifest !== null) {
|
|
2443
|
-
if (!manifest.isDynamic && this.videoElement !== null) {
|
|
2444
|
-
return this.videoElement.duration;
|
|
2445
|
-
}
|
|
2446
|
-
return manifest.getMaximumSafePosition();
|
|
2447
|
-
}
|
|
2448
|
-
return null;
|
|
2449
|
-
}
|
|
2450
|
-
|
|
2451
|
-
/**
|
|
2452
|
-
* /!\ For demo use only! Do not touch!
|
|
2453
|
-
*
|
|
2454
|
-
* Returns every chunk buffered for a given buffer type.
|
|
2455
|
-
* Returns `null` if no SegmentBuffer was created for this type of buffer.
|
|
2456
|
-
* @param {string} bufferType
|
|
2457
|
-
* @returns {Array.<Object>|null}
|
|
2458
|
-
*/
|
|
2459
|
-
__priv_getSegmentBufferContent(bufferType : IBufferType) : IBufferedChunk[] | null {
|
|
2460
|
-
if (this._priv_contentInfos === null ||
|
|
2461
|
-
this._priv_contentInfos.segmentBuffersStore === null)
|
|
2462
|
-
{
|
|
2463
|
-
return null;
|
|
2464
|
-
}
|
|
2465
|
-
const segmentBufferStatus = this._priv_contentInfos
|
|
2466
|
-
.segmentBuffersStore.getStatus(bufferType);
|
|
2467
|
-
if (segmentBufferStatus.type === "initialized") {
|
|
2468
|
-
segmentBufferStatus.value.synchronizeInventory(true);
|
|
2469
|
-
return segmentBufferStatus.value.getInventory();
|
|
2470
|
-
}
|
|
2471
|
-
return null;
|
|
2472
|
-
}
|
|
2473
|
-
|
|
2474
|
-
/**
|
|
2475
|
-
* Reset all state properties relative to a playing content.
|
|
2476
|
-
*/
|
|
2477
|
-
private _priv_cleanUpCurrentContentState() : void {
|
|
2478
|
-
log.debug("Locking `contentLock` to clean-up the current content.");
|
|
2479
|
-
|
|
2480
|
-
// lock playback of new contents while cleaning up is pending
|
|
2481
|
-
this._priv_contentLock.setValue(true);
|
|
2482
|
-
|
|
2483
|
-
this._priv_contentInfos?.mediaElementTrackChoiceManager?.dispose();
|
|
2484
|
-
this._priv_contentInfos = null;
|
|
2485
|
-
|
|
2486
|
-
this._priv_contentEventsMemory = {};
|
|
2487
|
-
|
|
2488
|
-
// DRM-related clean-up
|
|
2489
|
-
const freeUpContentLock = () => {
|
|
2490
|
-
if (this.videoElement !== null) { // If not disposed
|
|
2491
|
-
log.debug("Unlocking `contentLock`. Next content can begin.");
|
|
2492
|
-
this._priv_contentLock.setValue(false);
|
|
2493
|
-
}
|
|
2494
|
-
};
|
|
2495
|
-
|
|
2496
|
-
if (!isNullOrUndefined(this.videoElement)) {
|
|
2497
|
-
clearOnStop(this.videoElement).then(
|
|
2498
|
-
() => {
|
|
2499
|
-
log.debug("API: DRM session cleaned-up with success!");
|
|
2500
|
-
freeUpContentLock();
|
|
2501
|
-
},
|
|
2502
|
-
(err : unknown) => {
|
|
2503
|
-
log.error("API: An error arised when trying to clean-up the DRM session:" +
|
|
2504
|
-
(err instanceof Error ? err.toString() :
|
|
2505
|
-
"Unknown Error"));
|
|
2506
|
-
freeUpContentLock();
|
|
2507
|
-
});
|
|
2508
|
-
} else {
|
|
2509
|
-
freeUpContentLock();
|
|
2510
|
-
}
|
|
2511
|
-
}
|
|
2512
|
-
|
|
2513
|
-
/**
|
|
2514
|
-
* Triggered when the Manifest has been loaded for the current content.
|
|
2515
|
-
* Initialize various private properties and emit initial event.
|
|
2516
|
-
* @param {Object} contentInfos
|
|
2517
|
-
* @param {Object} manifest
|
|
2518
|
-
*/
|
|
2519
|
-
private _priv_onManifestReady(
|
|
2520
|
-
contentInfos : IPublicApiContentInfos,
|
|
2521
|
-
manifest : Manifest
|
|
2522
|
-
) : void {
|
|
2523
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2524
|
-
return; // Event for another content
|
|
2525
|
-
}
|
|
2526
|
-
contentInfos.manifest = manifest;
|
|
2527
|
-
const cancelSignal = contentInfos.currentContentCanceller.signal;
|
|
2528
|
-
this._priv_reloadingMetadata.manifest = manifest;
|
|
2529
|
-
|
|
2530
|
-
const { initialAudioTrack, initialTextTrack } = contentInfos;
|
|
2531
|
-
contentInfos.trackChoiceManager = new TrackChoiceManager({
|
|
2532
|
-
preferTrickModeTracks: this._priv_preferTrickModeTracks,
|
|
2533
|
-
});
|
|
2534
|
-
|
|
2535
|
-
const preferredAudioTracks = initialAudioTrack === undefined ?
|
|
2536
|
-
this._priv_preferredAudioTracks :
|
|
2537
|
-
[initialAudioTrack];
|
|
2538
|
-
contentInfos.trackChoiceManager.setPreferredAudioTracks(preferredAudioTracks, true);
|
|
2539
|
-
|
|
2540
|
-
const preferredTextTracks = initialTextTrack === undefined ?
|
|
2541
|
-
this._priv_preferredTextTracks :
|
|
2542
|
-
[initialTextTrack];
|
|
2543
|
-
contentInfos.trackChoiceManager.setPreferredTextTracks(preferredTextTracks, true);
|
|
2544
|
-
|
|
2545
|
-
contentInfos.trackChoiceManager
|
|
2546
|
-
.setPreferredVideoTracks(this._priv_preferredVideoTracks,
|
|
2547
|
-
true);
|
|
2548
|
-
manifest.addEventListener("manifestUpdate", (updates) => {
|
|
2549
|
-
// Update the tracks chosen if it changed
|
|
2550
|
-
if (contentInfos.trackChoiceManager !== null) {
|
|
2551
|
-
contentInfos.trackChoiceManager.update();
|
|
2552
|
-
}
|
|
2553
|
-
const currentPeriod = this._priv_contentInfos?.currentPeriod ?? undefined;
|
|
2554
|
-
const trackChoiceManager = this._priv_contentInfos?.trackChoiceManager;
|
|
2555
|
-
if (currentPeriod === undefined || isNullOrUndefined(trackChoiceManager)) {
|
|
2556
|
-
return;
|
|
2557
|
-
}
|
|
2558
|
-
for (const update of updates.updatedPeriods) {
|
|
2559
|
-
if (update.period.id === currentPeriod.id) {
|
|
2560
|
-
if (update.result.addedAdaptations.length > 0 ||
|
|
2561
|
-
update.result.removedAdaptations.length > 0)
|
|
2562
|
-
{
|
|
2563
|
-
// We might have new (or less) tracks, send events just to be sure
|
|
2564
|
-
const audioTracks = trackChoiceManager.getAvailableAudioTracks(currentPeriod);
|
|
2565
|
-
this._priv_triggerEventIfNotStopped("availableAudioTracksChange",
|
|
2566
|
-
audioTracks ?? [],
|
|
2567
|
-
cancelSignal);
|
|
2568
|
-
const textTracks = trackChoiceManager.getAvailableTextTracks(currentPeriod);
|
|
2569
|
-
this._priv_triggerEventIfNotStopped("availableTextTracksChange",
|
|
2570
|
-
textTracks ?? [],
|
|
2571
|
-
cancelSignal);
|
|
2572
|
-
const videoTracks = trackChoiceManager.getAvailableVideoTracks(currentPeriod);
|
|
2573
|
-
this._priv_triggerEventIfNotStopped("availableVideoTracksChange",
|
|
2574
|
-
videoTracks ?? [],
|
|
2575
|
-
cancelSignal);
|
|
2576
|
-
}
|
|
2577
|
-
}
|
|
2578
|
-
return;
|
|
2579
|
-
}
|
|
2580
|
-
}, contentInfos.currentContentCanceller.signal);
|
|
2581
|
-
}
|
|
2582
|
-
|
|
2583
|
-
/**
|
|
2584
|
-
* Triggered each times the current Period Changed.
|
|
2585
|
-
* Store and emit initial state for the Period.
|
|
2586
|
-
*
|
|
2587
|
-
* @param {Object} contentInfos
|
|
2588
|
-
* @param {Object} periodInfo
|
|
2589
|
-
*/
|
|
2590
|
-
private _priv_onActivePeriodChanged(
|
|
2591
|
-
contentInfos : IPublicApiContentInfos,
|
|
2592
|
-
{ period } : { period : Period }
|
|
2593
|
-
) : void {
|
|
2594
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2595
|
-
return; // Event for another content
|
|
2596
|
-
}
|
|
2597
|
-
contentInfos.currentPeriod = period;
|
|
2598
|
-
|
|
2599
|
-
const cancelSignal = contentInfos.currentContentCanceller.signal;
|
|
2600
|
-
if (this._priv_contentEventsMemory.periodChange !== period) {
|
|
2601
|
-
this._priv_contentEventsMemory.periodChange = period;
|
|
2602
|
-
this._priv_triggerEventIfNotStopped("periodChange", period, cancelSignal);
|
|
2603
|
-
}
|
|
2604
|
-
|
|
2605
|
-
this._priv_triggerEventIfNotStopped("availableAudioTracksChange",
|
|
2606
|
-
this.getAvailableAudioTracks(),
|
|
2607
|
-
cancelSignal);
|
|
2608
|
-
this._priv_triggerEventIfNotStopped("availableTextTracksChange",
|
|
2609
|
-
this.getAvailableTextTracks(),
|
|
2610
|
-
cancelSignal);
|
|
2611
|
-
this._priv_triggerEventIfNotStopped("availableVideoTracksChange",
|
|
2612
|
-
this.getAvailableVideoTracks(),
|
|
2613
|
-
cancelSignal);
|
|
2614
|
-
|
|
2615
|
-
const trackChoiceManager = this._priv_contentInfos?.trackChoiceManager;
|
|
2616
|
-
|
|
2617
|
-
// Emit intial events for the Period
|
|
2618
|
-
if (!isNullOrUndefined(trackChoiceManager)) {
|
|
2619
|
-
const audioTrack = trackChoiceManager.getChosenAudioTrack(period);
|
|
2620
|
-
this._priv_triggerEventIfNotStopped("audioTrackChange",
|
|
2621
|
-
audioTrack,
|
|
2622
|
-
cancelSignal);
|
|
2623
|
-
const textTrack = trackChoiceManager.getChosenTextTrack(period);
|
|
2624
|
-
this._priv_triggerEventIfNotStopped("textTrackChange",
|
|
2625
|
-
textTrack,
|
|
2626
|
-
cancelSignal);
|
|
2627
|
-
const videoTrack = trackChoiceManager.getChosenVideoTrack(period);
|
|
2628
|
-
this._priv_triggerEventIfNotStopped("videoTrackChange",
|
|
2629
|
-
videoTrack,
|
|
2630
|
-
cancelSignal);
|
|
2631
|
-
} else {
|
|
2632
|
-
this._priv_triggerEventIfNotStopped("audioTrackChange", null, cancelSignal);
|
|
2633
|
-
this._priv_triggerEventIfNotStopped("textTrackChange", null, cancelSignal);
|
|
2634
|
-
this._priv_triggerEventIfNotStopped("videoTrackChange", null, cancelSignal);
|
|
2635
|
-
}
|
|
2636
|
-
|
|
2637
|
-
this._priv_triggerAvailableBitratesChangeEvent("availableAudioBitratesChange",
|
|
2638
|
-
this.getAvailableAudioBitrates(),
|
|
2639
|
-
cancelSignal);
|
|
2640
|
-
if (contentInfos.currentContentCanceller.isUsed()) {
|
|
2641
|
-
return;
|
|
2642
|
-
}
|
|
2643
|
-
this._priv_triggerAvailableBitratesChangeEvent("availableVideoBitratesChange",
|
|
2644
|
-
this.getAvailableVideoBitrates(),
|
|
2645
|
-
cancelSignal);
|
|
2646
|
-
if (contentInfos.currentContentCanceller.isUsed()) {
|
|
2647
|
-
return;
|
|
2648
|
-
}
|
|
2649
|
-
const audioBitrate = this._priv_getCurrentRepresentations()?.audio?.bitrate ?? -1;
|
|
2650
|
-
this._priv_triggerCurrentBitrateChangeEvent("audioBitrateChange",
|
|
2651
|
-
audioBitrate,
|
|
2652
|
-
cancelSignal);
|
|
2653
|
-
if (contentInfos.currentContentCanceller.isUsed()) {
|
|
2654
|
-
return;
|
|
2655
|
-
}
|
|
2656
|
-
|
|
2657
|
-
const videoBitrate = this._priv_getCurrentRepresentations()?.video?.bitrate ?? -1;
|
|
2658
|
-
this._priv_triggerCurrentBitrateChangeEvent("videoBitrateChange",
|
|
2659
|
-
videoBitrate,
|
|
2660
|
-
cancelSignal);
|
|
2661
|
-
}
|
|
2662
|
-
|
|
2663
|
-
/**
|
|
2664
|
-
* Triggered each times a new "PeriodStream" is ready.
|
|
2665
|
-
* Choose the right Adaptation for the Period and emit it.
|
|
2666
|
-
* @param {Object} contentInfos
|
|
2667
|
-
* @param {Object} value
|
|
2668
|
-
*/
|
|
2669
|
-
private _priv_onPeriodStreamReady(
|
|
2670
|
-
contentInfos : IPublicApiContentInfos,
|
|
2671
|
-
value : {
|
|
2672
|
-
type : IBufferType;
|
|
2673
|
-
period : Period;
|
|
2674
|
-
adaptationRef : SharedReference<Adaptation|null|undefined>;
|
|
2675
|
-
}
|
|
2676
|
-
) : void {
|
|
2677
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2678
|
-
return; // Event for another content
|
|
2679
|
-
}
|
|
2680
|
-
const { type, period, adaptationRef } = value;
|
|
2681
|
-
const trackChoiceManager = contentInfos.trackChoiceManager;
|
|
2682
|
-
|
|
2683
|
-
switch (type) {
|
|
2684
|
-
|
|
2685
|
-
case "video":
|
|
2686
|
-
if (isNullOrUndefined(trackChoiceManager)) {
|
|
2687
|
-
log.error("API: TrackChoiceManager not instanciated for a new video period");
|
|
2688
|
-
adaptationRef.setValue(null);
|
|
2689
|
-
} else {
|
|
2690
|
-
trackChoiceManager.addPeriod(type, period, adaptationRef);
|
|
2691
|
-
trackChoiceManager.setInitialVideoTrack(period);
|
|
2692
|
-
}
|
|
2693
|
-
break;
|
|
2694
|
-
|
|
2695
|
-
case "audio":
|
|
2696
|
-
if (isNullOrUndefined(trackChoiceManager)) {
|
|
2697
|
-
log.error(`API: TrackChoiceManager not instanciated for a new ${type} period`);
|
|
2698
|
-
adaptationRef.setValue(null);
|
|
2699
|
-
} else {
|
|
2700
|
-
trackChoiceManager.addPeriod(type, period, adaptationRef);
|
|
2701
|
-
trackChoiceManager.setInitialAudioTrack(period);
|
|
2702
|
-
}
|
|
2703
|
-
break;
|
|
2704
|
-
|
|
2705
|
-
case "text":
|
|
2706
|
-
if (isNullOrUndefined(trackChoiceManager)) {
|
|
2707
|
-
log.error(`API: TrackChoiceManager not instanciated for a new ${type} period`);
|
|
2708
|
-
adaptationRef.setValue(null);
|
|
2709
|
-
} else {
|
|
2710
|
-
trackChoiceManager.addPeriod(type, period, adaptationRef);
|
|
2711
|
-
trackChoiceManager.setInitialTextTrack(period);
|
|
2712
|
-
}
|
|
2713
|
-
break;
|
|
2714
|
-
|
|
2715
|
-
default:
|
|
2716
|
-
const adaptations = period.adaptations[type];
|
|
2717
|
-
if (!isNullOrUndefined(adaptations) && adaptations.length > 0) {
|
|
2718
|
-
adaptationRef.setValue(adaptations[0]);
|
|
2719
|
-
} else {
|
|
2720
|
-
adaptationRef.setValue(null);
|
|
2721
|
-
}
|
|
2722
|
-
break;
|
|
2723
|
-
}
|
|
2724
|
-
}
|
|
2725
|
-
|
|
2726
|
-
/**
|
|
2727
|
-
* Triggered each times we "remove" a PeriodStream.
|
|
2728
|
-
* @param {Object} contentInfos
|
|
2729
|
-
* @param {Object} value
|
|
2730
|
-
*/
|
|
2731
|
-
private _priv_onPeriodStreamCleared(
|
|
2732
|
-
contentInfos : IPublicApiContentInfos,
|
|
2733
|
-
value : { type : IBufferType; period : Period }
|
|
2734
|
-
) : void {
|
|
2735
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2736
|
-
return; // Event for another content
|
|
2737
|
-
}
|
|
2738
|
-
const { type, period } = value;
|
|
2739
|
-
const trackChoiceManager = contentInfos.trackChoiceManager;
|
|
2740
|
-
|
|
2741
|
-
// Clean-up track choice from TrackChoiceManager
|
|
2742
|
-
switch (type) {
|
|
2743
|
-
case "audio":
|
|
2744
|
-
case "text":
|
|
2745
|
-
case "video":
|
|
2746
|
-
if (!isNullOrUndefined(trackChoiceManager)) {
|
|
2747
|
-
trackChoiceManager.removePeriod(type, period);
|
|
2748
|
-
}
|
|
2749
|
-
break;
|
|
2750
|
-
}
|
|
2751
|
-
|
|
2752
|
-
// Clean-up stored Representation and Adaptation information
|
|
2753
|
-
const { activeAdaptations, activeRepresentations } = contentInfos;
|
|
2754
|
-
if (!isNullOrUndefined(activeAdaptations) &&
|
|
2755
|
-
!isNullOrUndefined(activeAdaptations[period.id]))
|
|
2756
|
-
{
|
|
2757
|
-
const activePeriodAdaptations = activeAdaptations[period.id];
|
|
2758
|
-
delete activePeriodAdaptations[type];
|
|
2759
|
-
if (Object.keys(activePeriodAdaptations).length === 0) {
|
|
2760
|
-
delete activeAdaptations[period.id];
|
|
2761
|
-
}
|
|
2762
|
-
}
|
|
2763
|
-
|
|
2764
|
-
if (!isNullOrUndefined(activeRepresentations) &&
|
|
2765
|
-
!isNullOrUndefined(activeRepresentations[period.id]))
|
|
2766
|
-
{
|
|
2767
|
-
const activePeriodRepresentations = activeRepresentations[period.id];
|
|
2768
|
-
delete activePeriodRepresentations[type];
|
|
2769
|
-
if (Object.keys(activePeriodRepresentations).length === 0) {
|
|
2770
|
-
delete activeRepresentations[period.id];
|
|
2771
|
-
}
|
|
2772
|
-
}
|
|
2773
|
-
}
|
|
2774
|
-
|
|
2775
|
-
/**
|
|
2776
|
-
* Triggered each times a new Adaptation is considered for the current
|
|
2777
|
-
* content.
|
|
2778
|
-
* Store given Adaptation and emit it if from the current Period.
|
|
2779
|
-
* @param {Object} contentInfos
|
|
2780
|
-
* @param {Object} value
|
|
2781
|
-
*/
|
|
2782
|
-
private _priv_onAdaptationChange(
|
|
2783
|
-
contentInfos : IPublicApiContentInfos,
|
|
2784
|
-
{ type, adaptation, period } : { type : IBufferType;
|
|
2785
|
-
adaptation : Adaptation|null;
|
|
2786
|
-
period : Period; }
|
|
2787
|
-
) : void {
|
|
2788
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2789
|
-
return; // Event for another content
|
|
2790
|
-
}
|
|
2791
|
-
|
|
2792
|
-
// lazily create contentInfos.activeAdaptations
|
|
2793
|
-
if (contentInfos.activeAdaptations === null) {
|
|
2794
|
-
contentInfos.activeAdaptations = {};
|
|
2795
|
-
}
|
|
2796
|
-
|
|
2797
|
-
const { activeAdaptations, currentPeriod } = contentInfos;
|
|
2798
|
-
const activePeriodAdaptations = activeAdaptations[period.id];
|
|
2799
|
-
if (isNullOrUndefined(activePeriodAdaptations)) {
|
|
2800
|
-
activeAdaptations[period.id] = { [type]: adaptation };
|
|
2801
|
-
} else {
|
|
2802
|
-
activePeriodAdaptations[type] = adaptation;
|
|
2803
|
-
}
|
|
2804
|
-
|
|
2805
|
-
const { trackChoiceManager } = contentInfos;
|
|
2806
|
-
const cancelSignal = contentInfos.currentContentCanceller.signal;
|
|
2807
|
-
if (trackChoiceManager !== null &&
|
|
2808
|
-
currentPeriod !== null && !isNullOrUndefined(period) &&
|
|
2809
|
-
period.id === currentPeriod.id)
|
|
2810
|
-
{
|
|
2811
|
-
switch (type) {
|
|
2812
|
-
case "audio":
|
|
2813
|
-
const audioTrack = trackChoiceManager.getChosenAudioTrack(currentPeriod);
|
|
2814
|
-
this._priv_triggerEventIfNotStopped("audioTrackChange",
|
|
2815
|
-
audioTrack,
|
|
2816
|
-
cancelSignal);
|
|
2817
|
-
|
|
2818
|
-
const availableAudioBitrates = this.getAvailableAudioBitrates();
|
|
2819
|
-
this._priv_triggerAvailableBitratesChangeEvent("availableAudioBitratesChange",
|
|
2820
|
-
availableAudioBitrates,
|
|
2821
|
-
cancelSignal);
|
|
2822
|
-
break;
|
|
2823
|
-
case "text":
|
|
2824
|
-
const textTrack = trackChoiceManager.getChosenTextTrack(currentPeriod);
|
|
2825
|
-
this._priv_triggerEventIfNotStopped("textTrackChange", textTrack, cancelSignal);
|
|
2826
|
-
break;
|
|
2827
|
-
case "video":
|
|
2828
|
-
const videoTrack = trackChoiceManager.getChosenVideoTrack(currentPeriod);
|
|
2829
|
-
this._priv_triggerEventIfNotStopped("videoTrackChange",
|
|
2830
|
-
videoTrack,
|
|
2831
|
-
cancelSignal);
|
|
2832
|
-
|
|
2833
|
-
const availableVideoBitrates = this.getAvailableVideoBitrates();
|
|
2834
|
-
this._priv_triggerAvailableBitratesChangeEvent("availableVideoBitratesChange",
|
|
2835
|
-
availableVideoBitrates,
|
|
2836
|
-
cancelSignal);
|
|
2837
|
-
break;
|
|
2838
|
-
}
|
|
2839
|
-
}
|
|
2840
|
-
}
|
|
2841
|
-
|
|
2842
|
-
/**
|
|
2843
|
-
* Triggered each times a new Representation is considered during playback.
|
|
2844
|
-
*
|
|
2845
|
-
* Store given Representation and emit it if from the current Period.
|
|
2846
|
-
*
|
|
2847
|
-
* @param {Object} contentInfos
|
|
2848
|
-
* @param {Object} obj
|
|
2849
|
-
*/
|
|
2850
|
-
private _priv_onRepresentationChange(
|
|
2851
|
-
contentInfos : IPublicApiContentInfos,
|
|
2852
|
-
{ type, period, representation }: { type : IBufferType;
|
|
2853
|
-
period : Period;
|
|
2854
|
-
representation : Representation|null; }
|
|
2855
|
-
) : void {
|
|
2856
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2857
|
-
return; // Event for another content
|
|
2858
|
-
}
|
|
2859
|
-
|
|
2860
|
-
// lazily create contentInfos.activeRepresentations
|
|
2861
|
-
if (contentInfos.activeRepresentations === null) {
|
|
2862
|
-
contentInfos.activeRepresentations = {};
|
|
2863
|
-
}
|
|
2864
|
-
|
|
2865
|
-
const { activeRepresentations, currentPeriod } = contentInfos;
|
|
2866
|
-
|
|
2867
|
-
const activePeriodRepresentations = activeRepresentations[period.id];
|
|
2868
|
-
if (isNullOrUndefined(activePeriodRepresentations)) {
|
|
2869
|
-
activeRepresentations[period.id] = { [type]: representation };
|
|
2870
|
-
} else {
|
|
2871
|
-
activePeriodRepresentations[type] = representation;
|
|
2872
|
-
}
|
|
2873
|
-
|
|
2874
|
-
const bitrate = representation?.bitrate ?? -1;
|
|
2875
|
-
if (!isNullOrUndefined(period) &&
|
|
2876
|
-
currentPeriod !== null &&
|
|
2877
|
-
currentPeriod.id === period.id)
|
|
2878
|
-
{
|
|
2879
|
-
const cancelSignal = this._priv_contentInfos.currentContentCanceller.signal;
|
|
2880
|
-
if (type === "video") {
|
|
2881
|
-
this._priv_triggerCurrentBitrateChangeEvent("videoBitrateChange",
|
|
2882
|
-
bitrate,
|
|
2883
|
-
cancelSignal);
|
|
2884
|
-
} else if (type === "audio") {
|
|
2885
|
-
this._priv_triggerCurrentBitrateChangeEvent("audioBitrateChange",
|
|
2886
|
-
bitrate,
|
|
2887
|
-
cancelSignal);
|
|
2888
|
-
}
|
|
2889
|
-
}
|
|
2890
|
-
}
|
|
2891
|
-
|
|
2892
|
-
/**
|
|
2893
|
-
* Triggered each time a bitrate estimate is calculated.
|
|
2894
|
-
*
|
|
2895
|
-
* Emit it.
|
|
2896
|
-
*
|
|
2897
|
-
* @param {Object} value
|
|
2898
|
-
*/
|
|
2899
|
-
private _priv_onBitrateEstimationChange({
|
|
2900
|
-
type,
|
|
2901
|
-
bitrate,
|
|
2902
|
-
} : { type : IBufferType;
|
|
2903
|
-
bitrate : number|undefined; }
|
|
2904
|
-
) : void {
|
|
2905
|
-
if (bitrate !== undefined) {
|
|
2906
|
-
this._priv_bitrateInfos.lastBitrates[type] = bitrate;
|
|
2907
|
-
}
|
|
2908
|
-
this.trigger("bitrateEstimationChange", { type, bitrate });
|
|
2909
|
-
}
|
|
2910
|
-
|
|
2911
|
-
/**
|
|
2912
|
-
* Triggered each time a textTrack is added to the video DOM Element.
|
|
2913
|
-
*
|
|
2914
|
-
* Trigger the right Player Event.
|
|
2915
|
-
*
|
|
2916
|
-
* @param {Array.<TextTrackElement>} tracks
|
|
2917
|
-
*/
|
|
2918
|
-
private _priv_onNativeTextTracksNext(tracks : TextTrack[]) : void {
|
|
2919
|
-
this.trigger("nativeTextTracksChange", tracks);
|
|
2920
|
-
}
|
|
2921
|
-
|
|
2922
|
-
/**
|
|
2923
|
-
* Triggered each time the player state updates.
|
|
2924
|
-
*
|
|
2925
|
-
* Trigger the right Player Event.
|
|
2926
|
-
*
|
|
2927
|
-
* @param {string} newState
|
|
2928
|
-
*/
|
|
2929
|
-
private _priv_setPlayerState(newState : IPlayerState) : void {
|
|
2930
|
-
if (this.state !== newState) {
|
|
2931
|
-
this.state = newState;
|
|
2932
|
-
log.info("API: playerStateChange event", newState);
|
|
2933
|
-
this.trigger("playerStateChange", newState);
|
|
2934
|
-
}
|
|
2935
|
-
}
|
|
2936
|
-
|
|
2937
|
-
/**
|
|
2938
|
-
* Triggered each time a playback observation.
|
|
2939
|
-
*
|
|
2940
|
-
* Trigger the right Player Event
|
|
2941
|
-
*
|
|
2942
|
-
* @param {Object} contentInfos
|
|
2943
|
-
* @param {Object} observation
|
|
2944
|
-
*/
|
|
2945
|
-
private _priv_triggerPositionUpdate(
|
|
2946
|
-
contentInfos : IPublicApiContentInfos,
|
|
2947
|
-
observation : IPlaybackObservation
|
|
2948
|
-
) : void {
|
|
2949
|
-
if (contentInfos.contentId !== this._priv_contentInfos?.contentId) {
|
|
2950
|
-
return; // Event for another content
|
|
2951
|
-
}
|
|
2952
|
-
|
|
2953
|
-
const { isDirectFile, manifest } = contentInfos;
|
|
2954
|
-
if ((!isDirectFile && manifest === null) || isNullOrUndefined(observation)) {
|
|
2955
|
-
return;
|
|
2956
|
-
}
|
|
2957
|
-
|
|
2958
|
-
const maximumPosition = manifest !== null ? manifest.getMaximumSafePosition() :
|
|
2959
|
-
undefined;
|
|
2960
|
-
const positionData : IPositionUpdate = {
|
|
2961
|
-
position: observation.position,
|
|
2962
|
-
duration: observation.duration,
|
|
2963
|
-
playbackRate: observation.playbackRate,
|
|
2964
|
-
maximumBufferTime: maximumPosition,
|
|
2965
|
-
|
|
2966
|
-
// TODO bufferGap may be undefined
|
|
2967
|
-
bufferGap: observation.bufferGap === undefined ||
|
|
2968
|
-
!isFinite(observation.bufferGap) ?
|
|
2969
|
-
0 :
|
|
2970
|
-
observation.bufferGap,
|
|
2971
|
-
};
|
|
2972
|
-
|
|
2973
|
-
if (manifest !== null &&
|
|
2974
|
-
manifest.isLive &&
|
|
2975
|
-
observation.position > 0
|
|
2976
|
-
) {
|
|
2977
|
-
const ast = manifest.availabilityStartTime ?? 0;
|
|
2978
|
-
positionData.wallClockTime = observation.position + ast;
|
|
2979
|
-
const livePosition = manifest.getLivePosition();
|
|
2980
|
-
if (livePosition !== undefined) {
|
|
2981
|
-
positionData.liveGap = livePosition - observation.position;
|
|
2982
|
-
}
|
|
2983
|
-
} else if (isDirectFile && this.videoElement !== null) {
|
|
2984
|
-
const startDate = getStartDate(this.videoElement);
|
|
2985
|
-
if (startDate !== undefined) {
|
|
2986
|
-
positionData.wallClockTime = startDate + observation.position;
|
|
2987
|
-
}
|
|
2988
|
-
}
|
|
2989
|
-
this.trigger("positionUpdate", positionData);
|
|
2990
|
-
}
|
|
2991
|
-
|
|
2992
|
-
/**
|
|
2993
|
-
* Trigger one of the "availableBitratesChange" event only if it changed from
|
|
2994
|
-
* the previously stored value.
|
|
2995
|
-
* @param {string} event
|
|
2996
|
-
* @param {Array.<number>} newVal
|
|
2997
|
-
* @param {Object} currentContentCancelSignal
|
|
2998
|
-
*/
|
|
2999
|
-
private _priv_triggerAvailableBitratesChangeEvent(
|
|
3000
|
-
event : "availableAudioBitratesChange" | "availableVideoBitratesChange",
|
|
3001
|
-
newVal : number[],
|
|
3002
|
-
currentContentCancelSignal : CancellationSignal
|
|
3003
|
-
) : void {
|
|
3004
|
-
const prevVal = this._priv_contentEventsMemory[event];
|
|
3005
|
-
if (!currentContentCancelSignal.isCancelled() &&
|
|
3006
|
-
(prevVal === undefined || !areArraysOfNumbersEqual(newVal, prevVal)))
|
|
3007
|
-
{
|
|
3008
|
-
this._priv_contentEventsMemory[event] = newVal;
|
|
3009
|
-
this.trigger(event, newVal);
|
|
3010
|
-
}
|
|
3011
|
-
}
|
|
3012
|
-
|
|
3013
|
-
/**
|
|
3014
|
-
* Trigger one of the "bitrateChange" event only if it changed from the
|
|
3015
|
-
* previously stored value.
|
|
3016
|
-
* @param {string} event
|
|
3017
|
-
* @param {number} newVal
|
|
3018
|
-
* @param {Object} currentContentCancelSignal
|
|
3019
|
-
*/
|
|
3020
|
-
private _priv_triggerCurrentBitrateChangeEvent(
|
|
3021
|
-
event : "audioBitrateChange" | "videoBitrateChange",
|
|
3022
|
-
newVal : number,
|
|
3023
|
-
currentContentCancelSignal : CancellationSignal
|
|
3024
|
-
) : void {
|
|
3025
|
-
if (!currentContentCancelSignal.isCancelled() &&
|
|
3026
|
-
newVal !== this._priv_contentEventsMemory[event])
|
|
3027
|
-
{
|
|
3028
|
-
this._priv_contentEventsMemory[event] = newVal;
|
|
3029
|
-
this.trigger(event, newVal);
|
|
3030
|
-
}
|
|
3031
|
-
}
|
|
3032
|
-
|
|
3033
|
-
private _priv_getCurrentRepresentations(
|
|
3034
|
-
) : Partial<Record<IBufferType, Representation|null>> | null {
|
|
3035
|
-
if (this._priv_contentInfos === null) {
|
|
3036
|
-
return null;
|
|
3037
|
-
}
|
|
3038
|
-
const { currentPeriod, activeRepresentations } = this._priv_contentInfos;
|
|
3039
|
-
if (currentPeriod === null ||
|
|
3040
|
-
activeRepresentations === null ||
|
|
3041
|
-
isNullOrUndefined(activeRepresentations[currentPeriod.id]))
|
|
3042
|
-
{
|
|
3043
|
-
return null;
|
|
3044
|
-
}
|
|
3045
|
-
return activeRepresentations[currentPeriod.id];
|
|
3046
|
-
}
|
|
3047
|
-
|
|
3048
|
-
/**
|
|
3049
|
-
* @param {string} evt
|
|
3050
|
-
* @param {*} arg
|
|
3051
|
-
* @param {Object} currentContentCancelSignal
|
|
3052
|
-
*/
|
|
3053
|
-
private _priv_triggerEventIfNotStopped<TEventName extends keyof IPublicAPIEvent>(
|
|
3054
|
-
evt : TEventName,
|
|
3055
|
-
arg : IEventPayload<IPublicAPIEvent, TEventName>,
|
|
3056
|
-
currentContentCancelSignal : CancellationSignal
|
|
3057
|
-
) {
|
|
3058
|
-
if (!currentContentCancelSignal.isCancelled()) {
|
|
3059
|
-
this.trigger(evt, arg);
|
|
3060
|
-
}
|
|
3061
|
-
}
|
|
3062
|
-
|
|
3063
|
-
/**
|
|
3064
|
-
* @param {Object} defaultAudioTrack
|
|
3065
|
-
* @param {Object} defaultTextTrack
|
|
3066
|
-
* @param {Object} cancelSignal
|
|
3067
|
-
* @returns {Object}
|
|
3068
|
-
*/
|
|
3069
|
-
private _priv_initializeMediaElementTrackChoiceManager(
|
|
3070
|
-
defaultAudioTrack : IAudioTrackPreference | null | undefined,
|
|
3071
|
-
defaultTextTrack : ITextTrackPreference | null | undefined,
|
|
3072
|
-
cancelSignal : CancellationSignal
|
|
3073
|
-
) : MediaElementTrackChoiceManager {
|
|
3074
|
-
assert(features.directfile !== null,
|
|
3075
|
-
"Initializing `MediaElementTrackChoiceManager` without Directfile feature");
|
|
3076
|
-
assert(this.videoElement !== null,
|
|
3077
|
-
"Initializing `MediaElementTrackChoiceManager` on a disposed RxPlayer");
|
|
3078
|
-
|
|
3079
|
-
const mediaElementTrackChoiceManager =
|
|
3080
|
-
new features.directfile.mediaElementTrackChoiceManager(this.videoElement);
|
|
3081
|
-
|
|
3082
|
-
const preferredAudioTracks = defaultAudioTrack === undefined ?
|
|
3083
|
-
this._priv_preferredAudioTracks :
|
|
3084
|
-
[defaultAudioTrack];
|
|
3085
|
-
mediaElementTrackChoiceManager.setPreferredAudioTracks(preferredAudioTracks, true);
|
|
3086
|
-
|
|
3087
|
-
const preferredTextTracks = defaultTextTrack === undefined ?
|
|
3088
|
-
this._priv_preferredTextTracks :
|
|
3089
|
-
[defaultTextTrack];
|
|
3090
|
-
mediaElementTrackChoiceManager.setPreferredTextTracks(preferredTextTracks, true);
|
|
3091
|
-
|
|
3092
|
-
mediaElementTrackChoiceManager
|
|
3093
|
-
.setPreferredVideoTracks(this._priv_preferredVideoTracks, true);
|
|
3094
|
-
|
|
3095
|
-
this._priv_triggerEventIfNotStopped(
|
|
3096
|
-
"availableAudioTracksChange",
|
|
3097
|
-
mediaElementTrackChoiceManager.getAvailableAudioTracks(),
|
|
3098
|
-
cancelSignal);
|
|
3099
|
-
this._priv_triggerEventIfNotStopped(
|
|
3100
|
-
"availableVideoTracksChange",
|
|
3101
|
-
mediaElementTrackChoiceManager.getAvailableVideoTracks(),
|
|
3102
|
-
cancelSignal);
|
|
3103
|
-
this._priv_triggerEventIfNotStopped(
|
|
3104
|
-
"availableTextTracksChange",
|
|
3105
|
-
mediaElementTrackChoiceManager.getAvailableTextTracks(),
|
|
3106
|
-
cancelSignal);
|
|
3107
|
-
this._priv_triggerEventIfNotStopped(
|
|
3108
|
-
"audioTrackChange",
|
|
3109
|
-
mediaElementTrackChoiceManager.getChosenAudioTrack() ?? null,
|
|
3110
|
-
cancelSignal);
|
|
3111
|
-
this._priv_triggerEventIfNotStopped(
|
|
3112
|
-
"textTrackChange",
|
|
3113
|
-
mediaElementTrackChoiceManager.getChosenTextTrack() ?? null,
|
|
3114
|
-
cancelSignal);
|
|
3115
|
-
this._priv_triggerEventIfNotStopped(
|
|
3116
|
-
"videoTrackChange",
|
|
3117
|
-
mediaElementTrackChoiceManager.getChosenVideoTrack() ?? null,
|
|
3118
|
-
cancelSignal);
|
|
3119
|
-
|
|
3120
|
-
mediaElementTrackChoiceManager
|
|
3121
|
-
.addEventListener("availableVideoTracksChange", (val) =>
|
|
3122
|
-
this.trigger("availableVideoTracksChange", val));
|
|
3123
|
-
mediaElementTrackChoiceManager
|
|
3124
|
-
.addEventListener("availableAudioTracksChange", (val) =>
|
|
3125
|
-
this.trigger("availableAudioTracksChange", val));
|
|
3126
|
-
mediaElementTrackChoiceManager
|
|
3127
|
-
.addEventListener("availableTextTracksChange", (val) =>
|
|
3128
|
-
this.trigger("availableTextTracksChange", val));
|
|
3129
|
-
|
|
3130
|
-
mediaElementTrackChoiceManager
|
|
3131
|
-
.addEventListener("audioTrackChange", (val) =>
|
|
3132
|
-
this.trigger("audioTrackChange", val));
|
|
3133
|
-
mediaElementTrackChoiceManager
|
|
3134
|
-
.addEventListener("videoTrackChange", (val) =>
|
|
3135
|
-
this.trigger("videoTrackChange", val));
|
|
3136
|
-
mediaElementTrackChoiceManager
|
|
3137
|
-
.addEventListener("textTrackChange", (val) =>
|
|
3138
|
-
this.trigger("textTrackChange", val));
|
|
3139
|
-
|
|
3140
|
-
return mediaElementTrackChoiceManager;
|
|
3141
|
-
}
|
|
3142
|
-
}
|
|
3143
|
-
Player.version = /* PLAYER_VERSION */"3.33.0";
|
|
3144
|
-
|
|
3145
|
-
/** Every events sent by the RxPlayer's public API. */
|
|
3146
|
-
interface IPublicAPIEvent {
|
|
3147
|
-
playerStateChange : string;
|
|
3148
|
-
positionUpdate : IPositionUpdate;
|
|
3149
|
-
audioTrackChange : IAudioTrack | null;
|
|
3150
|
-
textTrackChange : ITextTrack | null;
|
|
3151
|
-
videoTrackChange : IVideoTrack | null;
|
|
3152
|
-
audioBitrateChange : number;
|
|
3153
|
-
videoBitrateChange : number;
|
|
3154
|
-
imageTrackUpdate : { data: IBifThumbnail[] };
|
|
3155
|
-
fullscreenChange : boolean;
|
|
3156
|
-
bitrateEstimationChange : IBitrateEstimate;
|
|
3157
|
-
volumeChange : number;
|
|
3158
|
-
error : IPlayerError | Error;
|
|
3159
|
-
warning : IPlayerError | Error;
|
|
3160
|
-
nativeTextTracksChange : TextTrack[];
|
|
3161
|
-
periodChange : IPeriod;
|
|
3162
|
-
availableAudioBitratesChange : number[];
|
|
3163
|
-
availableVideoBitratesChange : number[];
|
|
3164
|
-
availableAudioTracksChange : IAvailableAudioTrack[];
|
|
3165
|
-
availableTextTracksChange : IAvailableTextTrack[];
|
|
3166
|
-
availableVideoTracksChange : IAvailableVideoTrack[];
|
|
3167
|
-
decipherabilityUpdate : IDecipherabilityUpdateContent[];
|
|
3168
|
-
play: null;
|
|
3169
|
-
pause: null;
|
|
3170
|
-
seeking : null;
|
|
3171
|
-
seeked : null;
|
|
3172
|
-
streamEvent : IStreamEvent;
|
|
3173
|
-
streamEventSkip : IStreamEvent;
|
|
3174
|
-
inbandEvents : IInbandEvent[];
|
|
3175
|
-
}
|
|
3176
|
-
|
|
3177
|
-
/** State linked to a particular contents loaded by the public API. */
|
|
3178
|
-
interface IPublicApiContentInfos {
|
|
3179
|
-
/**
|
|
3180
|
-
* Unique identifier for this `IPublicApiContentInfos` object.
|
|
3181
|
-
* Allows to identify and thus compare this `contentInfos` object with another
|
|
3182
|
-
* one.
|
|
3183
|
-
*/
|
|
3184
|
-
contentId : string;
|
|
3185
|
-
/** Original URL set to load the content. */
|
|
3186
|
-
originalUrl : string | undefined;
|
|
3187
|
-
/** `ContentInitializer` used to load the content. */
|
|
3188
|
-
initializer : ContentInitializer;
|
|
3189
|
-
/** TaskCanceller triggered when it's time to stop the current content. */
|
|
3190
|
-
currentContentCanceller : TaskCanceller;
|
|
3191
|
-
/**
|
|
3192
|
-
* `true` if the current content is in DirectFile mode.
|
|
3193
|
-
* `false` is the current content has a transport protocol (Smooth/DASH...).
|
|
3194
|
-
*/
|
|
3195
|
-
isDirectFile : boolean;
|
|
3196
|
-
/**
|
|
3197
|
-
* Current Image Track Data associated to the content.
|
|
3198
|
-
* `null` if the current content has no image playlist linked to it.
|
|
3199
|
-
* @deprecated
|
|
3200
|
-
*/
|
|
3201
|
-
thumbnails : IBifThumbnail[]|null;
|
|
3202
|
-
/**
|
|
3203
|
-
* Manifest linked to the current content.
|
|
3204
|
-
* `null` if the current content loaded has no manifest or if the content is
|
|
3205
|
-
* not yet loaded.
|
|
3206
|
-
*/
|
|
3207
|
-
manifest : Manifest|null;
|
|
3208
|
-
/**
|
|
3209
|
-
* Current Period being played.
|
|
3210
|
-
* `null` if no Period is being played.
|
|
3211
|
-
*/
|
|
3212
|
-
currentPeriod : Period|null;
|
|
3213
|
-
/**
|
|
3214
|
-
* Store currently considered adaptations, per active period.
|
|
3215
|
-
* `null` if no Adaptation is active
|
|
3216
|
-
*/
|
|
3217
|
-
activeAdaptations : {
|
|
3218
|
-
[periodId : string] : Partial<Record<IBufferType, Adaptation|null>>;
|
|
3219
|
-
} | null;
|
|
3220
|
-
/**
|
|
3221
|
-
* Store currently considered representations, per active period.
|
|
3222
|
-
* `null` if no Representation is active
|
|
3223
|
-
*/
|
|
3224
|
-
activeRepresentations : {
|
|
3225
|
-
[periodId : string] : Partial<Record<IBufferType, Representation|null>>;
|
|
3226
|
-
} | null;
|
|
3227
|
-
/** Store starting audio track if one. */
|
|
3228
|
-
initialAudioTrack : undefined|IAudioTrackPreference;
|
|
3229
|
-
/** Store starting text track if one. */
|
|
3230
|
-
initialTextTrack : undefined|ITextTrackPreference;
|
|
3231
|
-
/** Keep information on the active SegmentBuffers. */
|
|
3232
|
-
segmentBuffersStore : SegmentBuffersStore | null;
|
|
3233
|
-
/**
|
|
3234
|
-
* TrackChoiceManager instance linked to the current content.
|
|
3235
|
-
* `null` if no content has been loaded or if the current content loaded
|
|
3236
|
-
* has no TrackChoiceManager.
|
|
3237
|
-
*/
|
|
3238
|
-
trackChoiceManager : TrackChoiceManager|null;
|
|
3239
|
-
/**
|
|
3240
|
-
* MediaElementTrackChoiceManager instance linked to the current content.
|
|
3241
|
-
* `null` if no content has been loaded or if the current content loaded
|
|
3242
|
-
* has no MediaElementTrackChoiceManager.
|
|
3243
|
-
*/
|
|
3244
|
-
mediaElementTrackChoiceManager : MediaElementTrackChoiceManager|null;
|
|
3245
|
-
}
|
|
3246
|
-
|
|
3247
|
-
export default Player;
|