Function description

The MediaPlayer Kit is a powerful player that supports playing local and online media resources. With this player, you can either locally play media resources or synchronously share currently playing media resources with remote users in the Agora channel.

Usage notice

  • Currently supported media formats: Local files in AVI, MP4, MP3, MKV, and FLV formats; Online media streams using RTMP and RTSP protocols.
  • When locally playing media resources, you only need a separate MediaPlayer Kit. When synchronously sharing media resources with remote users, you need to use the MediaPlayer Kit, Agora Native SDK, and RtcChannelPublishPlugin at the same time. The MediaPlayer Kit supports the local user to use the player function, the Native SDK supports real-time live broadcast scenarios, and the RtcChannelPublishPlugin supports publishing media streams to remote users in Agora channel.
  • When sharing media resources with remote users, the playback window occupies the local user's video as captured by the camera. Therefore, if you want remote users to see both the local user's and the player's window, you need to start another process to capture the local user's video.

Set up the development environment

Prerequisites

  • Microsoft Visual Studio 2015 or later
  • A Windows device running Windows 7 or later

Open the specified ports in Firewall Requirements if your network has a firewall.

A valid Agora account (Sign up for free) is necessary when sharing media resources to remote users.

Create a Windows project

Build a Windows project from scratch:

Create a Windows project
  1. Open Microsoft Visual Studio and click Create new project.
  2. On the New Project panel, choose MFC Application as the project type, input the project name, choose the project location, and click OK.
  3. On the MFC Application panel, choose Application type > Dialog based, and click Finish.

Integrate the MediaPlayer Kit

Configure the project files

  1. Go to Downloads, download the latest version of the MediaPlayer Kit, and unzip the download package.

  2. Copy the sdk to the project folder.

Configure the project properties

Right-click the project name in the Solution Explorer window, click Properties to configure the following project properties, and click OK.

  • Go to the VC++ > General > Additional Include Directories menu, click Edit, and input ./sdk/include in the pop-up window.
  • Go to the VC++ > General > Additional Library Directories menu, click Edit, and input ./sdk/lib in the pop-up window.
  • Go to the Linker > Input > Additional Dependencies menu, click Edit, and input AgoraMediaPlayer.lib and shell32.lib in the pop-up window.

Integrate the Native SDK

Integrate the RtcChannelPublishPlugin

Version requirements: The same as the Native SDK version series you are using.

Integration steps:

  1. Download and unzip the MediaPlayerExtensions.zip.
  2. Add the ./MediaPlayerExtensions/win/RtcChannelPublishHelper folder to your project folder.
  3. Right-click the project name in the Solution Explorer window, click Properties to configure the following project properties, and click OK: Go to the VC++ > General > Additional Include Directories menu, click Edit, and input ./RtcChannelPublishPlugin/utils in the pop-up window.

Implementation

Play media resources locally

After integrating the MediaPlayer Kit, follow these steps to implement the local playback function.

Create a player instance

  1. Call the createAgoraMediaPlayer method to create an instance of IMediaPlayer.

    To play different media resources simultaneously, you should create multiple instances.

  2. Call the initialize method to initialize the player.

Set the log file

The log file contains all the log events generated by the mediaplayer kit at runtime. The default path of the log file is C:/Users/{user_name}/AppData/Local/Agora/{project_name}.

Set the log file as follows:

  • To set the output path of the log file, call the setLogFile method of the IMediaPlayer class.
  • To set the output level of the log file, call the setLogFilter method of the IMediaPlayer class .

Register a player observer object

  1. Implement the IMediaPlayerObserver interface and instantiate an IMediaPlayerObserver object.
  2. Call the registerPlayerObserver method of the IMediaPlayer class to register a player observer object and listen for the following playback events:
    • onPositionChanged, which reports the current playback progress.
    • onPlayerStateChanged, which reports the playback state change.
    • onPlayerEvent, which reports the events during playback, such as the result of a seek operation to a new playback position, and the change of the audio track.
    • onMetaData, which occurs each time the player receives the media metadata.

By listening for these events, you can have more control over the playback process and enable your app to support data in custom formats (media metadata). If an exception occurs, you can use these event callbacks for troubleshooting.

(Optional) Register an audio observer object

  1. Implement the IAudioFrameObserver interface and instantiate an IAudioFrameObserver object.

  2. Call the registerAudioFrameObserver method of the IMediaPlayer class to register an audio observer object and listen for the event that confirms the reception of each audio frame. After handling the AudioPcmFrameclass, you can record the audio.

(Optional) Register a video observer object

  1. Implement the IVideoFrameObserver interface and instantiate an IVideoFrameObserver object.
  2. Call the registerVideoFrameObserver method of the IMediaPlayer class to register a video observer object and listen for the event that confirms the reception of each video frame. After handling the VideoFrame class, you can record the video or take screenshots of the video.

Preparations for playback

  1. Call the setView method of the IMediaPlayer class to set the render view of the player.

  2. Call the setRenderMode method of the IMediaPlayer class to set the rendering mode of the player's view.

  3. Call the open method of the IMediaPlayer class to open the media resource. The media resource path can be a network path or a local path. Both absolute and relative paths are supported.

    Do not proceed until you receive the onPlayerStateChanged callback reporting PLAYER_STATE_OPEN_COMPLETED(2).

  4. Call the play method of the IMediaPlayer class to play the media resource locally.

Adjust playback settings

You can call several other methods of the IMediaPlayer class to implement various playback settings:

  • Pause/resume playback, adjust playback progress and speed, adjust local playback volume, and so on.
  • Get the total duration of the media resource, get the current playback progress, get the current playback state, get the number of media streams in the media resource and detailed information about each media stream.

Stop playback

  1. Call the stop method of the IMediaPlayer class to stop playback.

  2. Call the unregisterAudioFrameObserver method of the IMediaPlayer class to stop registering the audio observer.

    If you have not registered an audio observer, skip this step.

  3. Call the unregisterVideoFrameObserver method of the IMediaPlayer class to stop registering the video observer.

    If you have not registered a video observer, skip this step.

  4. Call the unregisterPlayerObserver method of the IMediaPlayer class to stop registering the player observer.

  5. Call the release method of the IMediaPlayer class to release the IMediaPlayer resource.

Sample code


class CPlayerSimpleDemo : public CWnd, public agora::rtc::IMediaPlayerObserver {
public:
    DECLARE_MESSAGE_MAP()
    CPlayerSimpleDemo() : media_player_( nullptr )
    {
    }


    ~CPlayerSimpleDemo()
    {
        if ( media_player_ )
        {
            media_player_->Release();
            media_player_ = nullptr;
        }
    }


    // IMediaPlayerObserver
    virtual void onPlayerStateChanged( const IMediaPlayer::PLAYER_STATE state,
                       const IMediaPlayer::PLAYER_ERROR ec ) override
    {
        switch ( state )
        {
        case IMediaPlayer::PLAYER_STATE_OPEN_COMPLETE:
            media_player_->play();
            break;
        case IMediaPlayer::PLAYER_STATE_FAILED:
            media_player_->stop();
            break;
        case IMediaPlayer::PLAYER_STATE_PLAYBACKCOMPLETED:
            media_player_->stop();
            break;
        default:
            break;
        }
    }


    virtual void onPositionChanged( const int64_t position ) override
    {
    }


    virtual void onMetaData( void* data, int length ) override
    {
    }


    virtual void onPlayerEvent( const IMediaPlayer::PLAYER_EVENT event ) override
    {
    }


    afx_msg int OnCreate( LPCREATESTRUCT lpCreateStruct )
    {
        if ( CWnd::OnCreate( lpCreateStruct ) == -1 )
            return(-1);
        media_player_ = createAgoraMediaPlayer();
        if ( media_player_ )
        {
            media_player_->registerPlayerObserver( this );
            media_player_->setView( m_hWnd );
            media_player_->open( "http://tb-video.bdstatic.com/tieba-smallvideo/68_20df3a646ab5357464cd819ea987763a.mp4" );
        }
        return(0);
    }


private:
    agora::rtc::IMediaPlayer* media_player_;
};

Share media resources to the remote

After integrating the MediaPlayer Kit, the Agora Native SDK, and the RtcChannelPublishPlugin, follow these steps to synchronously share media resources played by the local user to all the remote users in the Agora channel.

Instantiate required objects

  1. Instantiate an IRtcEngine object.
  2. Instantiate the objects for the mediaplayer kit and the RtcChannelPublishPlugin.
  3. Call the attachPlayerToRtc method of the AgoraRtcChannelPublishHelper class to bundle the player with the Agora channel.

Enable the player to complete playback preparations

Register the player, audio, and video observer objects, and complete the preparations for playback. See Play media resources locally for details.

Do not proceed until you receive the onPlayerStateChanged callback reporting PLAYER_STATE_PLAYING (3).

Enable the local user to join the channel by using the SDK

Refer to the RTC quickstart guide for details about how to enable the local user to join the live broadcast channel in the role of BROADCASTER:

  1. Call the setChannelProfile method to set the channel mode to live broadcast.

  2. Call the setClientRole method to set the local user role as the broadcaster.

  3. Call the enableVideo method to enable the video module.

  4. Call the joinChannel method to enable the local user to join the channel.

    Do not proceed until you receive the onJoinChannelSuccess callback.

Start sharing by using the plugin

  1. To prevent the remote user from hearing the echo, call the adjustPlayoutSignalVolume method to set the playback volume to 0, and then call the mute(true) method of the IMediaPlayer class.

  2. Call the publishVideo/publishAudio method to publish the video/audio stream in the media resource to remote users in the Agora channel.

  3. Call the adjustPublishSignalVolume method to adjust the playback volume heard by the remote user.

Cancel sharing by using the plugin

  1. Call the unpublishVideo/unpublishAudio method to unpublish the video/audio stream in the media resource.

  2. Call the detachPlayerFromRtc method to unbind the player from the Agora channel.

Do not skip this section and directly call the leaveChannel method to cancel the media stream being shared, otherwise abnormal behaviors occur when the local user rejoins the channel:
  • The previously unshared media stream automatically sends to the remote users.
  • The audio and video streams are not synchronized during playback.
  • Sample code

    AgoraRtcChannelPublishHelper *agora_rtc_channel_publish_helper_= new AgoraRtcChannelPublishHelper()
    virtual void onPlayerStateChanged( const IMediaPlayer::PLAYER_STATE state,
                       const IMediaPlayer::PLAYER_ERROR ec ) override
    {
        switch ( state )
        {
        case IMediaPlayer::PLAYER_STATE_OPEN_COMPLETE:
            agora_rtc_channel_publish_helper_->attachPlayerToRtc(rtc_engine_, media_player_);
            agora_rtc_channel_publish_helper_->publishAudio();
            agora_rtc_channel_publish_helper_->publishVideo();
            break;
        case IMediaPlayer::PLAYER_STATE_FAILED:
            media_player_->stop();
            break;
        case IMediaPlayer::PLAYER_STATE_PLAYBACKCOMPLETED:
            media_player_->stop();
            break;
        default:
            break;
        }
    }

    Considerations

    To avoid the problem that the new audio router is abnormally muted when the local user switches the audio router during playback, Agora recommends the following steps:

    • When playing media resources locally, Agora recommends that the local user does not switch the audio router to Bluetooth devices.

    • When sharing media resources, Agora recommends the following steps before switching the audio router to Bluetooth devices:

      1. After calling the joinChannel method, call the enumeratePlaybackDevices method to get the deviceId of the Bluetooth device.
      2. Call the setPlaybackDevice method and pass in the deviceId parameter to switch the audio router to the Bluetooth device during playback.

    API documentation

    See the API documentation.