]> git.saurik.com Git - wxWidgets.git/blame - samples/mediaplayer/mediaplayer.cpp
attempts to suppress C4702 for VC
[wxWidgets.git] / samples / mediaplayer / mediaplayer.cpp
CommitLineData
ff4aedc5 1///////////////////////////////////////////////////////////////////////////////
a2d9b7d0 2// Name: mediaplayer.cpp
eaf0d558
RN
3// Purpose: wxMediaCtrl sample
4// Author: Ryan Norton
5// Modified by:
6// Created: 11/10/04
7// RCS-ID: $Id$
8// Copyright: (c) Ryan Norton
9// Licence: wxWindows licence
ff4aedc5
RN
10///////////////////////////////////////////////////////////////////////////////
11
12// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
13// MediaPlayer
14//
15// This is a simple example of how to use all the funtionality of
16// the wxMediaCtrl class in wxWidgets.
17//
18// To use this sample, simply select Open File from the file menu,
19// select the file you want to play - and MediaPlayer will play the file,
20// showing video if neccessary.
21//
22// You can select one of the menu options, or move the slider around
23// to manipulate what is playing.
24// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
eaf0d558
RN
25
26// ============================================================================
ff4aedc5 27// Definitions
eaf0d558
RN
28// ============================================================================
29
30// ----------------------------------------------------------------------------
ff4aedc5 31// Pre-compiled header stuff
eaf0d558
RN
32// ----------------------------------------------------------------------------
33
eaf0d558
RN
34#include "wx/wxprec.h"
35
36#ifdef __BORLANDC__
37 #pragma hdrstop
38#endif
39
eaf0d558
RN
40#ifndef WX_PRECOMP
41 #include "wx/wx.h"
42#endif
43
44// ----------------------------------------------------------------------------
ff4aedc5 45// Headers
eaf0d558
RN
46// ----------------------------------------------------------------------------
47
d0b9eaa2
RN
48#include "wx/mediactrl.h" //for wxMediaCtrl
49#include "wx/filedlg.h" //for opening files from OpenFile
50#include "wx/slider.h" //for a slider for seeking within media
51#include "wx/sizer.h" //for positioning controls/wxBoxSizer
52#include "wx/timer.h" //timer for updating status bar
53#include "wx/textdlg.h" //for getting user text from OpenURL
eaf0d558 54
ff4aedc5
RN
55// ----------------------------------------------------------------------------
56// Bail out if the user doesn't want one of the
57// things we need
58// ----------------------------------------------------------------------------
eaf0d558 59
ff4aedc5
RN
60#if !wxUSE_GUI
61#error "This is a GUI sample"
eaf0d558
RN
62#endif
63
ff4aedc5
RN
64#if !wxUSE_MEDIACTRL || !wxUSE_MENUS || !wxUSE_SLIDER || !wxUSE_TIMER
65#error "menus, slider, mediactrl, and timers must all enabled for this sample!"
66#endif
67
68// ============================================================================
d0b9eaa2 69// Declarations
ff4aedc5
RN
70// ============================================================================
71
72// ----------------------------------------------------------------------------
73// Enumurations
74// ----------------------------------------------------------------------------
75
76// IDs for the controls and the menu commands
77enum
78{
79 // menu items
80 wxID_LOOP = 1,
81 wxID_OPENFILE,
82 wxID_PLAY,
83 wxID_PAUSE,
84// wxID_STOP, [built-in to wxWidgets]
85// wxID_ABOUT, [built-in to wxWidgets]
86// wxID_EXIT, [built-in to wxWidgets]
87
88 // id for our slider
89 wxID_SLIDER,
90
91 // id for our wxMediaCtrl
92 wxID_MEDIACTRL
93};
94
95// ----------------------------------------------------------------------------
96// MyApp
eaf0d558
RN
97// ----------------------------------------------------------------------------
98
eaf0d558
RN
99class MyApp : public wxApp
100{
101public:
eaf0d558
RN
102 virtual bool OnInit();
103};
104
ff4aedc5
RN
105// ----------------------------------------------------------------------------
106// MyFrame
107// ----------------------------------------------------------------------------
108
eaf0d558
RN
109class MyFrame : public wxFrame
110{
111public:
ff4aedc5 112 // Ctor/Dtor
eaf0d558
RN
113 MyFrame(const wxString& title);
114 ~MyFrame();
115
ff4aedc5 116 // Menu event handlers
eaf0d558
RN
117 void OnQuit(wxCommandEvent& event);
118 void OnAbout(wxCommandEvent& event);
119 void OnLoop(wxCommandEvent& event);
120
121 void OnOpenFile(wxCommandEvent& event);
122 void OnOpenURL(wxCommandEvent& event);
123
124 void OnPlay(wxCommandEvent& event);
125 void OnPause(wxCommandEvent& event);
126 void OnStop(wxCommandEvent& event);
127
ff4aedc5 128 // Slider event handlers
eaf0d558
RN
129 void OnSeek(wxCommandEvent& event);
130
ff4aedc5
RN
131 // Media event handlers
132 void OnMediaStop(wxMediaEvent& event);
eaf0d558
RN
133
134private:
ff4aedc5 135 // Rebuild base status string (see Implementation)
d0b9eaa2
RN
136 void ResetStatus();
137
ff4aedc5
RN
138 wxMediaCtrl* m_mediactrl; //Our media control
139 wxSlider* m_slider; //The slider below our media control
140 class MyTimer* m_timer; //Timer to write info to status bar
141 wxString m_basestatus; //Base status string (see ResetStatus())
142 int m_nLoops; //Counter, incremented each time media loops
143
144 // So that mytimer can access MyFrame's members
eaf0d558 145 friend class MyTimer;
ff4aedc5 146};
eaf0d558 147
ff4aedc5
RN
148// ----------------------------------------------------------------------------
149// MyTimer
150// ----------------------------------------------------------------------------
151
152class MyTimer : public wxTimer
153{
154public:
155 //Ctor
156 MyTimer(MyFrame* frame) {m_frame = frame;}
eaf0d558 157
ff4aedc5
RN
158 //Called each time the timer's timeout expires
159 void Notify();
160
161 MyFrame* m_frame; //The MyFrame
eaf0d558
RN
162};
163
ff4aedc5 164// ============================================================================
d0b9eaa2 165//
ff4aedc5 166// Implementation
d0b9eaa2 167//
ff4aedc5 168// ============================================================================
d0b9eaa2 169
ff4aedc5
RN
170// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
171//
172// [Functions]
d0b9eaa2 173//
ff4aedc5
RN
174// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
175
176// ----------------------------------------------------------------------------
177// wxGetMediaStateText
d0b9eaa2 178//
ff4aedc5
RN
179// Converts a wxMediaCtrl state into something useful that we can display
180// to the user
181// ----------------------------------------------------------------------------
eaf0d558
RN
182const wxChar* wxGetMediaStateText(int nState)
183{
184 switch(nState)
185 {
186 case wxMEDIASTATE_PLAYING:
187 return wxT("Playing");
188 case wxMEDIASTATE_STOPPED:
189 return wxT("Stopped");
190 ///case wxMEDIASTATE_PAUSED:
191 default:
192 return wxT("Paused");
193 }
194}
195
ff4aedc5
RN
196// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
197//
198// MyApp
199//
200// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
eaf0d558
RN
201
202// ----------------------------------------------------------------------------
ff4aedc5
RN
203// This sets up this wxApp as the global wxApp that gui calls in wxWidgets
204// use. For example, if you were to be in windows and use a file dialog,
205// wxWidgets would use wxTheApp->GetHInstance() which would get the instance
206// handle of the application. These routines in wx _DO NOT_ check to see if
207// the wxApp exists, and thus will crash the application if you try it.
208//
209// IMPLEMENT_APP does this, and also implements the platform-specific entry
210// routine, such as main or WinMain(). Use IMPLEMENT_APP_NO_MAIN if you do
211// not desire this behavior.
eaf0d558 212// ----------------------------------------------------------------------------
eaf0d558
RN
213IMPLEMENT_APP(MyApp)
214
eaf0d558
RN
215
216// ----------------------------------------------------------------------------
ff4aedc5
RN
217// MyApp::OnInit
218//
219// Where execution starts - akin to a main or WinMain.
220// 1) Create the frame and show it to the user
221// 2) return true specifying that we want execution to continue past OnInit
eaf0d558 222// ----------------------------------------------------------------------------
eaf0d558
RN
223bool MyApp::OnInit()
224{
ff4aedc5 225 MyFrame *frame = new MyFrame(_T("MediaPlayer wxWidgets Sample"));
eaf0d558
RN
226 frame->Show(true);
227
eaf0d558
RN
228 return true;
229}
230
eaf0d558 231
ff4aedc5
RN
232// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
233//
234// MyFrame
d0b9eaa2 235//
ff4aedc5
RN
236// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
237
238// ----------------------------------------------------------------------------
239// MyFrame Constructor
d0b9eaa2 240//
ff4aedc5
RN
241// 1) Create our menus
242// 2) Create our controls and add them to some sizers
243// 3) Create our status bar
244// 4) Connect our events
245// 5) Start our timer
246// ----------------------------------------------------------------------------
eaf0d558 247MyFrame::MyFrame(const wxString& title)
ff4aedc5 248 : wxFrame(NULL, wxID_ANY, title)
eaf0d558 249{
d0b9eaa2
RN
250 //
251 // Create Menus
252 //
eaf0d558
RN
253 wxMenu *menuFile = new wxMenu;
254
eaf0d558 255 wxMenu *helpMenu = new wxMenu;
ff4aedc5
RN
256 helpMenu->Append(wxID_ABOUT,
257 _T("&About...\tF1"),
258 _T("Show about dialog"));
eaf0d558 259
ff4aedc5 260 menuFile->Append(wxID_OPENFILE, _T("&Open File"), _T("Open a File"));
eaf0d558 261 menuFile->AppendSeparator();
ff4aedc5
RN
262 menuFile->Append(wxID_PLAY, _T("&Play"), _T("Resume playback"));
263 menuFile->Append(wxID_PAUSE, _T("P&ause"), _T("Pause playback"));
264 menuFile->Append(wxID_STOP, _T("&Stop"), _T("Stop playback"));
eaf0d558 265 menuFile->AppendSeparator();
ff4aedc5
RN
266 menuFile->AppendCheckItem(wxID_LOOP,
267 _T("&Loop"),
268 _T("Loop Selected Media"));
eaf0d558 269 menuFile->AppendSeparator();
ff4aedc5
RN
270 menuFile->Append(wxID_EXIT,
271 _T("E&xit\tAlt-X"),
272 _T("Quit this program"));
eaf0d558 273
eaf0d558
RN
274 wxMenuBar *menuBar = new wxMenuBar();
275 menuBar->Append(menuFile, _T("&File"));
276 menuBar->Append(helpMenu, _T("&Help"));
277
eaf0d558 278 SetMenuBar(menuBar);
eaf0d558 279
d0b9eaa2
RN
280 //
281 // Create and attach the first/main sizer
282 //
ff4aedc5
RN
283 wxBoxSizer* vertsizer = new wxBoxSizer(wxVERTICAL);
284 this->SetSizer(vertsizer);
eaf0d558
RN
285 this->SetAutoLayout(true);
286
d0b9eaa2
RN
287 //
288 // Create our media control
289 //
ff4aedc5
RN
290 m_mediactrl = new wxMediaCtrl(this, wxID_MEDIACTRL);
291 vertsizer->Add(m_mediactrl, 0, wxALIGN_CENTER_HORIZONTAL|wxALL, 5);
d0b9eaa2
RN
292
293 //
294 // Create our slider
295 //
ff4aedc5 296 m_slider = new wxSlider(this, wxID_SLIDER, 0, //init
ceefc965
WS
297 0, //start
298 0, //end
299 wxDefaultPosition, wxDefaultSize,
eaf0d558 300 wxSL_HORIZONTAL );
ff4aedc5 301 vertsizer->Add(m_slider, 0, wxALIGN_CENTER_HORIZONTAL|wxALL|wxEXPAND , 5);
eaf0d558 302
d0b9eaa2
RN
303
304 //
305 // Create the second sizer which will position things
ceefc965 306 // vertically -
d0b9eaa2
RN
307 //
308 // -------Menu----------
309 // [m_mediactrl]
310 //
311 // [m_slider]
312 //
eaf0d558 313 wxBoxSizer* horzsizer = new wxBoxSizer(wxHORIZONTAL);
ff4aedc5 314 vertsizer->Add(horzsizer, 0, wxALIGN_CENTER_HORIZONTAL|wxALL, 5);
eaf0d558 315
d0b9eaa2
RN
316 //
317 // Create our status bar
318 //
eaf0d558
RN
319#if wxUSE_STATUSBAR
320 // create a status bar just for fun (by default with 1 pane only)
321 CreateStatusBar(1);
322 ResetStatus();
323 SetStatusText(m_basestatus);
324#endif // wxUSE_STATUSBAR
ff4aedc5
RN
325
326 //
327 // Connect events.
328 //
329 // There are two ways in wxWidgets to use events -
330 // Message Maps and Connections.
331 //
332 // Message Maps are implemented by putting
333 // DECLARE_MESSAGE_MAP in your wxEvtHandler-derived
334 // class you want to use for events, such as MyFrame.
335 //
336 // Then after your class declaration you put
337 // BEGIN_EVENT_TABLE(MyFrame, wxFrame)
338 // EVT_XXX(XXX)...
339 // END_EVENT_TABLE()
340 //
341 // Where MyFrame is the class with the DECLARE_MESSAGE_MAP
342 // in it. EVT_XXX(XXX) are each of your handlers, such
343 // as EVT_MENU for menu events and the XXX inside
344 // is the parameters to the event macro - in the case
345 // of EVT_MENU the menu id and then the function to call.
346 //
347 // However, with wxEvtHandler::Connect you can avoid a
348 // global message map for your class and those annoying
349 // macros. You can also change the context in which
350 // the call the handler (more later).
351 //
352 // The downside is that due to the limitation that
353 // wxWidgets doesn't use templates in certain areas,
354 // You have to triple-cast the event function.
355 //
356 // There are five parameters to wxEvtHandler::Connect -
357 //
358 // The first is the id of the instance whose events
359 // you want to handle - i.e. a menu id for menus,
360 // a control id for controls (wxControl::GetId())
361 // and so on.
362 //
363 // The second is the event id. This is the same
364 // as the message maps (EVT_MENU) except prefixed
365 // with "wx" (wxEVT_MENU).
366 //
367 // The third is the function handler for the event -
368 // You need to cast it to the specific event handler
369 // type, then to a wxEventFunction, then to a
370 // wxObjectEventFunction - I.E.
371 // (wxObjectEventFunction)(wxEventFunction)
372 // (wxCommandEventFunction) &MyFrame::MyHandler
373 //
374 // The fourth is an optional userdata param -
375 // this is of historical relevance only and is
376 // there only for backwards compatability.
377 //
378 // The fifth is the context in which to call the
379 // handler - by default (this param is optional)
380 // this. For example in your event handler
381 // if you were to call "this->MyFunc()"
382 // it would literally do this->MyFunc. However,
383 // if you were to pass myHandler as the fifth
384 // parameter, for instance, you would _really_
385 // be calling myHandler->MyFunc, even though
386 // the compiler doesn't really know it.
387 //
d0b9eaa2
RN
388
389 //
ff4aedc5 390 // Menu events
d0b9eaa2 391 //
ff4aedc5
RN
392 this->Connect(wxID_EXIT, wxEVT_COMMAND_MENU_SELECTED,
393 (wxObjectEventFunction) (wxEventFunction)
394 (wxCommandEventFunction) &MyFrame::OnQuit);
395
396 this->Connect(wxID_ABOUT, wxEVT_COMMAND_MENU_SELECTED,
397 (wxObjectEventFunction) (wxEventFunction)
398 (wxCommandEventFunction) &MyFrame::OnAbout);
399
400 this->Connect(wxID_LOOP, wxEVT_COMMAND_MENU_SELECTED,
401 (wxObjectEventFunction) (wxEventFunction)
402 (wxCommandEventFunction) &MyFrame::OnLoop);
403
404 this->Connect(wxID_OPENFILE, wxEVT_COMMAND_MENU_SELECTED,
405 (wxObjectEventFunction) (wxEventFunction)
406 (wxCommandEventFunction) &MyFrame::OnOpenFile);
d0b9eaa2 407
ff4aedc5
RN
408 this->Connect(wxID_PLAY, wxEVT_COMMAND_MENU_SELECTED,
409 (wxObjectEventFunction) (wxEventFunction)
410 (wxCommandEventFunction) &MyFrame::OnPlay);
411
412 this->Connect(wxID_PAUSE, wxEVT_COMMAND_MENU_SELECTED,
413 (wxObjectEventFunction) (wxEventFunction)
414 (wxCommandEventFunction) &MyFrame::OnPause);
415
416 this->Connect(wxID_STOP, wxEVT_COMMAND_MENU_SELECTED,
417 (wxObjectEventFunction) (wxEventFunction)
418 (wxCommandEventFunction) &MyFrame::OnStop);
419
420
421 //
422 // Slider events
423 //
424 this->Connect(wxID_SLIDER, wxEVT_COMMAND_SLIDER_UPDATED,
425 (wxObjectEventFunction) (wxEventFunction)
426 (wxCommandEventFunction) &MyFrame::OnSeek);
427
428 //
429 // Media Control events
430 //
431 this->Connect(wxID_MEDIACTRL, wxEVT_MEDIA_STOP,
432 (wxObjectEventFunction) (wxEventFunction)
433 (wxCommandEventFunction) &MyFrame::OnMediaStop);
434
435 //
436 // End of Events
437 //
438
439 //
440 // Set our loop counter to 0
441 //
442 m_nLoops = 0;
443
444 //
445 // Create a timer to update our status bar
446 //
d0b9eaa2
RN
447 m_timer = new MyTimer(this);
448 m_timer->Start(100);
eaf0d558
RN
449}
450
ff4aedc5
RN
451// ----------------------------------------------------------------------------
452// MyFrame Destructor
d0b9eaa2 453//
ff4aedc5
RN
454// 1) Deletes child objects implicitly
455// 2) Delete our timer explicitly
456// ----------------------------------------------------------------------------
eaf0d558
RN
457MyFrame::~MyFrame()
458{
d0b9eaa2 459 delete m_timer;
eaf0d558
RN
460}
461
ff4aedc5
RN
462// ----------------------------------------------------------------------------
463// MyFrame::ResetStatus
464//
465// Here we just make a simple status string with some useful info about
466// the media that we won't change later - such as the length of the media.
467//
468// We then append some other info that changes in MyTimer::Notify, then
469// set the status bar to this text.
d0b9eaa2 470//
ff4aedc5
RN
471// In real applications, you'd want to find a better way to do this,
472// such as static text controls (wxStaticText).
473//
474// We display info here in seconds (wxMediaCtrl uses milliseconds - that's why
475// we divide by 1000).
476//
477// We also reset our loop counter here.
478// ----------------------------------------------------------------------------
479void MyFrame::ResetStatus()
480{
481 m_basestatus = wxString::Format(_T("Size(x,y):%i,%i ")
482 _T("Length(Seconds):%u Speed:%1.1fx"),
483 m_mediactrl->GetBestSize().x,
484 m_mediactrl->GetBestSize().y,
485 (unsigned)((m_mediactrl->GetDuration() / 1000).ToLong()),
486 m_mediactrl->GetPlaybackRate()
487 );
488
489 m_slider->SetRange(0, (m_mediactrl->GetDuration() / 1000).ToLong());
490
491 m_nLoops = 0;
492}
493
494// ----------------------------------------------------------------------------
495// MyFrame::OnQuit
d0b9eaa2 496//
ff4aedc5
RN
497// Called from file->quit.
498// Closes this application.
499// ----------------------------------------------------------------------------
eaf0d558
RN
500void MyFrame::OnQuit(wxCommandEvent& WXUNUSED(event))
501{
502 // true is to force the frame to close
503 Close(true);
504}
505
ff4aedc5
RN
506// ----------------------------------------------------------------------------
507// MyFrame::OnAbout
508//
509// Called from help->about.
510// Gets some info about this application.
511// ----------------------------------------------------------------------------
eaf0d558
RN
512void MyFrame::OnAbout(wxCommandEvent& WXUNUSED(event))
513{
514 wxString msg;
515 msg.Printf( _T("This is a test of wxMediaCtrl.\n")
516 _T("Welcome to %s"), wxVERSION_STRING);
517
518 wxMessageBox(msg, _T("About wxMediaCtrl test"), wxOK | wxICON_INFORMATION, this);
519}
520
ff4aedc5
RN
521// ----------------------------------------------------------------------------
522// MyFrame::OnLoop
d0b9eaa2 523//
ff4aedc5
RN
524// Called from file->loop.
525// Changes the state of whether we want to loop or not.
526// ----------------------------------------------------------------------------
eaf0d558
RN
527void MyFrame::OnLoop(wxCommandEvent& WXUNUSED(event))
528{
ff4aedc5 529 m_mediactrl->Loop( !m_mediactrl->IsLooped() );
eaf0d558
RN
530}
531
ff4aedc5
RN
532// ----------------------------------------------------------------------------
533// MyFrame::OnOpenFile
d0b9eaa2 534//
ff4aedc5
RN
535// Called from file->openfile.
536// Opens and plays a media file
537// ----------------------------------------------------------------------------
eaf0d558
RN
538void MyFrame::OnOpenFile(wxCommandEvent& WXUNUSED(event))
539{
540 wxFileDialog fd(this);
541
542 if(fd.ShowModal() == wxID_OK)
543 {
d0b9eaa2 544 if( !m_mediactrl->Load(fd.GetPath()) )
eaf0d558
RN
545 wxMessageBox(wxT("Couldn't load file!"));
546
d0b9eaa2 547 if( !m_mediactrl->Play() )
ceefc965
WS
548 wxMessageBox(wxT("Couldn't play movie!"));
549
eaf0d558
RN
550 ResetStatus();
551 }
552}
553
ff4aedc5
RN
554// ----------------------------------------------------------------------------
555// MyFrame::OnPlay
556//
557// Called from file->play.
558// Resumes the media if it is paused or stopped.
559// ----------------------------------------------------------------------------
eaf0d558
RN
560void MyFrame::OnPlay(wxCommandEvent& WXUNUSED(event))
561{
d0b9eaa2 562 if( !m_mediactrl->Play() )
eaf0d558
RN
563 wxMessageBox(wxT("Couldn't play movie!"));
564}
565
ff4aedc5
RN
566// ----------------------------------------------------------------------------
567// MyFrame::OnPause
568//
569// Called from file->pause.
570// Pauses the media in-place.
571// ----------------------------------------------------------------------------
eaf0d558
RN
572void MyFrame::OnPause(wxCommandEvent& WXUNUSED(event))
573{
d0b9eaa2 574 if( !m_mediactrl->Pause() )
eaf0d558
RN
575 wxMessageBox(wxT("Couldn't pause movie!"));
576}
577
ff4aedc5
RN
578// ----------------------------------------------------------------------------
579// MyFrame::OnStop
580//
581// Called from file->stop.
582// Where it stops depends on whether you can seek in the
583// media control or not - if you can it stops and seeks to the beginning,
584// otherwise it will appear to be at the end - but it will start over again
585// when Play() is called
586// ----------------------------------------------------------------------------
eaf0d558
RN
587void MyFrame::OnStop(wxCommandEvent& WXUNUSED(event))
588{
d0b9eaa2 589 if( !m_mediactrl->Stop() )
eaf0d558
RN
590 wxMessageBox(wxT("Couldn't stop movie!"));
591}
592
ff4aedc5
RN
593// ----------------------------------------------------------------------------
594// MyFrame::OnSeek
595//
596// Called from file->seek.
597// Called when the user moves the slider -
598// seeks to a position within the media
599// ----------------------------------------------------------------------------
eaf0d558
RN
600void MyFrame::OnSeek(wxCommandEvent& WXUNUSED(event))
601{
d0b9eaa2 602 if( !m_mediactrl->SetPosition( m_slider->GetValue() * 1000 ) )
eaf0d558
RN
603 wxMessageBox(wxT("Couldn't seek in movie!"));
604}
605
ff4aedc5
RN
606// ----------------------------------------------------------------------------
607// MyFrame::OnMediaStop
608//
609// Called when the media is about to stop playing.
610// Here we just increase our loop counter
611// ----------------------------------------------------------------------------
612void MyFrame::OnMediaStop(wxMediaEvent& WXUNUSED(event))
613{
614 ++m_nLoops;
615}
616
617// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
d0b9eaa2 618//
ff4aedc5 619// MyTimer
d0b9eaa2 620//
ff4aedc5
RN
621// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
622
623// ----------------------------------------------------------------------------
624// MyTimer::Notify
625//
626// 1) Update our slider with the position were are in in the media
627// 2) Update our status bar with the base text from MyFrame::ResetStatus,
628// append some non-static (changing) info to it, then set the
629// status bar text to that result
630// ----------------------------------------------------------------------------
631void MyTimer::Notify()
eaf0d558 632{
ff4aedc5
RN
633 long lPosition = (m_frame->m_mediactrl->GetPosition() / 1000).ToLong();
634 m_frame->m_slider->SetValue(lPosition);
635
636#if wxUSE_STATUSBAR
637 m_frame->SetStatusText(wxString::Format(
638 _T("%s Pos:%u State:%s Loops:%i"),
639 m_frame->m_basestatus.c_str(),
640 (unsigned int)lPosition,
641 wxGetMediaStateText(m_frame->m_mediactrl->GetState()),
642 m_frame->m_nLoops
643 )
644 );
645#endif
ceefc965 646}
ff4aedc5
RN
647
648//
649// End of MediaPlayer sample
650//