Managing Media Servers (Windows CE 5.0)
The Media Query Engine (MQE) supports multiple media servers on a local network. It allows an application to enumerate all locally available servers and select one of them to be the source of media content.
The MQE internally maintains a list of UPnP Media Servers it has discovered. It notifies the host application about new server discoveries. The user can choose any of the available servers to be source of media content through the user interface provided by the host application.
Changing the Maximum Number of Media Servers
If are is running your NMD in a subnet that has many media servers, you can change the MQEs registry entry NumMaxServers to list more than the default max number of servers (10).
HKEY_LOCAL_MACHINE\Software\MediaQueryEngine
NumMaxServers
Starting and Stopping the Media Query Engine
The Initialize and Start steps bring the MQE to the Running state where it is fully functional.
The following table shows the MQE states.
State | Description |
---|---|
Un-Initialized | No memory allocated |
Stopped | Allocated memory to support event sink registration |
Running | Allocated resources needed. Actively searching for upnp servers, delivering events and making media queries as requested. |
Error | Error encountered during state transition, e.g. memory allocation error. |
The following code sample demonstrates how to start the MQE.
If( MediaQueryEn[gine_t::Initialize() )
{
MediaQueryEngine_t::AddSink( <Your MQE Sink > );
if( MediaQueryEngine_t::Start() )
{
//MQE is Running – CreateNewQuery, KnownMediaServers
}
else
{
//Try freeing some memory, uninitialize MQE and initialize and try
//again
}
}
Else
{
//Try freeing some memory, uninitialize MQE and try again
}
Stopping the MQE
void Main_t::UnInitMQELib()
{
MediaQueryEngine_t::Stop();
//Release MQE related resources
delete[] m_ItemBatches;
delete[] m_SavedQueries;
MediaQueryEngine_t::UnInitialize();
}
Getting Server Information
User would call the KnownMediaServers function to access media server information. The known media servers information is returned as a ServerInfoCollection object. You can iterate over the collection to get specific information.
Void Settings_t::ShowAllKnownMediaServers()
{
m_ServerInfoCollection = MediaQueryEngine_t::KnownMediaServers();
for( int Index=0; Index< m_ServerInfoColection.TotalServers(); ++Index)
{
ServerInfo_t Sinfo = m_ServerInfoCollection.GetServerInfo( Index );
// Call Sinfo.UniqueDeviceName(), Sinfo.FriendlyDeviceName(),
//Sinfo.DeviceStatus() to get the information to display
//Provides means for end user to activate one of the attached
//servers
}
}
Void Settings_t::UserSelectedOptionToActivateAServer(int ServerIndex)
{
ServerInfo_t Sinfo = m_ServerInfoCollection.GetServerInfo(ServerIndex);
Sinfo.Activate();
//Return value of Activate would indicate if the operation
//was successful.
//MQE will send ActiveServerChanged notification if the requested
//server is activated
}
Managing Content Metadata
In UPnP terminology, the MQE acts as a control point. It searches for UPnP Media Servers and provides an NMD media meta-data about available media. One of the meta-data is URL for the media item. Using the URL, you can stream or download media data and play it on your device. There is a limit of 260 characters for streaming media URLs.
Managing Event Notifications
The MQE provides the host application with information about changes in network status, device authorization, and server status via events. When a UPnP server goes down, the MQE informs the host application about the loss of the server. Also, when content at the server changes, the MQE notifies the host application about the change.
The MQE registers with the selected media server to receive this information.
To receive the events, you call AddSink. To stop receiving the events you call RemoveSink.
Class UserSink_t:public QueryEngineSink_t
{
void
SinkProc(
QueryEngineEvents_e event
long AdditionalInfo
)
{
<Your Code>
}
}
Queries
Each query session with a media server is represented as a MediaQuery object. The query object does memory management for the data retrieved from server. Each item in the Media Library is represented as a MediaItem object, allowing access to the content's meta-data.
The result of a query can be a large number of media items, on the order of 10,000 or more. In order to utilize memory and network resources efficiently and have a good response time, The Media Query Engine downloads result sets in batches. A batch is represented by MediaItemBatch_t object.
You call the function CreateNewQuery to get media data. The resulting data is organized in batches. You call GetNextBatch on the MediaQuery object to get a batch of media items. Calling GetMediaItem on the MediaItemBatch returns a MediaItem object. This is demonstrated in the following code:
Void GetData_t::GetAllMusicData( )
{
QueryParams_t QueryParam(Music,
SearchBy_None,
NULL,SortBy_None,
s_BatchSize);
m_CurrentQuery = MediaQueryEngine_t::CreateNewQuery(QueryParam);
if( m_CurrentQuery.IsValid() )
{
//Display number of results – m_CurrentQuery.TotalItems()
//Use m_CurrentQuery.GetNextBatch() to retrieve a media item batch
}
}
Void GetData_t::ShowQueryResult()
{
MediaItemBatch_t CurrentBatch = m_CurrentQuery.GetNextBatch();
for( int Index=0; Index < CurrentBatch.TotalItems(); ++Index )
{
MediaItem_t MediaItem = CurrentBatch.GetMediaItem(Index);
if( MediaItem.GetItemAttribute(Attr_Title,
<Your Buffer>,
<Your Buffer Length>)
{
SendMessage(m_ListBox, LB_INSERTSTRING, <Your Buffer>, -1 );
}
else
{
//check buffer length
}
}
}
See Also
Send Feedback on this topic to the authors