diff --git a/src/apps/mediaplayer/Constants.h b/src/apps/mediaplayer/Constants.h new file mode 100644 index 0000000000..e46520f416 --- /dev/null +++ b/src/apps/mediaplayer/Constants.h @@ -0,0 +1,28 @@ +#ifndef CONSTANTS_H +#define CONSTANTS_H + +#include +#include + +#define APP_SIGNATURE "application/x-vnd.obos.media-player" + +// File menu +const uint32 MENU_OPEN_FILE ='MFof'; +const uint32 MENU_OPEN_URL ='MFou'; +const uint32 MENU_FILE_INFO ='MFfi'; +const uint32 MENU_CLOSE ='MFcl'; +const uint32 MENU_QUIT ='MFqu'; + +// View menu +const uint32 MENU_MINI_MODE ='MVmm'; +const uint32 MENU_HALF_SCALE ='MVhs'; +const uint32 MENU_NORMAL_SCALE ='MVns'; +const uint32 MENU_DOUBLE_SCALE ='MVds'; +const uint32 MENU_FULL_SCREEN ='MVfs'; + +// Settings menu +const uint32 MENU_PREFERENCES ='MSpr'; +const uint32 MENU_LOOP ='MSlp'; +const uint32 MENU_PRESERVE_VIDEO_TIMING ='MSvt'; + +#endif // CONSTANTS_H diff --git a/src/apps/mediaplayer/Jamfile b/src/apps/mediaplayer/Jamfile index d983b92709..280a4da4cd 100644 --- a/src/apps/mediaplayer/Jamfile +++ b/src/apps/mediaplayer/Jamfile @@ -8,6 +8,8 @@ AddResources MediaPlayer : App MediaPlayer : MediaPlayerApp.cpp + MediaPlayerView.cpp + MediaPlayerWindow.cpp ; LinkSharedOSLibs MediaPlayer : be media tracker ; diff --git a/src/apps/mediaplayer/MediaPlayerApp.cpp b/src/apps/mediaplayer/MediaPlayerApp.cpp new file mode 100644 index 0000000000..aa8326db14 --- /dev/null +++ b/src/apps/mediaplayer/MediaPlayerApp.cpp @@ -0,0 +1,189 @@ + +#include +#include +#include +#include +#include + +#include "Constants.h" +#include "MediaPlayerApp.h" +#include "MediaPlayerWindow.h" + +using namespace BPrivate; + +const int cascade_left = 7; +const int cascade_top = 26; +const int cascade_step = 15; + +BRect windowRect(cascade_left-cascade_step,cascade_top-cascade_step,507,426); + +void cascade() { + BScreen screen(NULL); + BRect screenBorder = screen.Frame(); + float left = windowRect.left + cascade_step; + if (left + windowRect.Width() > screenBorder.right) { + left = cascade_left; + } + float top = windowRect.top + cascade_step; + if (top + windowRect.Height() > screenBorder.bottom) { + top = cascade_top; + } + windowRect.OffsetTo(BPoint(left,top)); +} + +void uncascade() { + BScreen screen(NULL); + BRect screenBorder = screen.Frame(); + float left = windowRect.left - cascade_step; + if (left < cascade_left) { + left = screenBorder.right - windowRect.Width() - cascade_left; + left = left - ((int)left % cascade_step) + cascade_left; + } + float top = windowRect.top - cascade_step; + if (top < cascade_top) { + top = screenBorder.bottom - windowRect.Height() - cascade_top; + top = top - ((int)left % cascade_step) + cascade_top; + } + windowRect.OffsetTo(BPoint(left,top)); +} + +MediaPlayerApp * media_player_app; + +MediaPlayerApp::MediaPlayerApp() + : BApplication(APP_SIGNATURE) +{ + fOpenPanel = new BFilePanel(); + + fWindowCount = 0; + media_player_app = this; +} + +void MediaPlayerApp::DispatchMessage(BMessage *msg, BHandler *handler) +{ + if ( msg->what == B_ARGV_RECEIVED ) { + int32 argc; + if (msg->FindInt32("argc",&argc) != B_OK) { + argc = 0; + } + const char ** argv = new (const char*)[argc]; + for (int arg = 0; (arg < argc) ; arg++) { + if (msg->FindString("argv",arg,&argv[arg]) != B_OK) { + argv[arg] = ""; + } + } + const char * cwd; + if (msg->FindString("cwd",&cwd) != B_OK) { + cwd = ""; + } + ArgvReceived(argc, argv, cwd); + } else { + BApplication::DispatchMessage(msg,handler); + } +} + +void +MediaPlayerApp::MessageReceived(BMessage *message) +{ + switch(message->what) { + case B_SILENT_RELAUNCH: + be_roster->ActivateApp(Team()); + break; + default: + BApplication::MessageReceived(message); + break; + } +} + +void +MediaPlayerApp::OpenDocument() +{ + cascade(); + new MediaPlayerWindow(windowRect); + fWindowCount++; +} + +void +MediaPlayerApp::OpenDocument(entry_ref * ref) +{ + cascade(); + new MediaPlayerWindow(windowRect,ref); + fWindowCount++; +} + +void +MediaPlayerApp::CloseDocument() +{ + uncascade(); + fWindowCount--; + if (fWindowCount == 0) { + BAutolock lock(this); + Quit(); + } +} + +void +MediaPlayerApp::RefsReceived(BMessage *message) +{ + int32 refNum; + entry_ref ref; + + refNum = 0; + while (message->FindRef("refs", refNum, &ref) == B_OK) { + OpenDocument(&ref); + refNum++; + } +} + +void +MediaPlayerApp::ArgvReceived(int32 argc, const char *argv[], const char * cwd) +{ + for (int i = 1 ; (i < argc) ; i++) { + BPath path; + if (argv[i][0] == '/') { + path.SetTo(argv[i]); + } else { + path.SetTo(cwd,argv[i]); + } + if (path.InitCheck() != B_OK) { + printf("path.InitCheck failed: \""); + if (argv[i][0] == '/') { + printf("%s",argv[i]); + } else { + printf("%s/%s",cwd,argv[i]); + } + printf("\".\n"); + continue; + } + + entry_ref ref; + if (get_ref_for_path(path.Path(), &ref) != B_OK) { + printf("get_ref_for_path failed: \""); + printf("%s",path.Path()); + printf("\".\n"); + continue; + } + OpenDocument(&ref); + } +} + +void +MediaPlayerApp::ReadyToRun() +{ + if (fWindowCount == 0) { + OpenDocument(); + } +} + +int32 +MediaPlayerApp::NumberOfWindows() +{ + return fWindowCount; +} + +int +main() +{ + MediaPlayerApp mediaPlayer; + mediaPlayer.Run(); + return 0; +} diff --git a/src/apps/mediaplayer/MediaPlayerApp.h b/src/apps/mediaplayer/MediaPlayerApp.h new file mode 100644 index 0000000000..7f3dd0b44c --- /dev/null +++ b/src/apps/mediaplayer/MediaPlayerApp.h @@ -0,0 +1,33 @@ +#ifndef MEDIA_PLAYER_APP +#define MEDIA_PLAYER_APP + +#include +#include +#include + +class MediaPlayerApp + : public BApplication +{ +public: + MediaPlayerApp(); + virtual void MessageReceived(BMessage *message); + virtual void ArgvReceived(int32 argc, const char *argv[], const char * cwd); + virtual void RefsReceived(BMessage *message); + virtual void ReadyToRun(); + + virtual void DispatchMessage(BMessage *an_event, BHandler *handler); + + int32 NumberOfWindows(); + void OpenDocument(); + void OpenDocument(entry_ref * ref); + void CloseDocument(); + +private: + BFilePanel *fOpenPanel; + int32 fWindowCount; + +}; + +extern MediaPlayerApp * media_player_app; + +#endif // MEDIA_PLAYER_APP diff --git a/src/apps/mediaplayer/MediaPlayerView.cpp b/src/apps/mediaplayer/MediaPlayerView.cpp new file mode 100644 index 0000000000..893bc68c14 --- /dev/null +++ b/src/apps/mediaplayer/MediaPlayerView.cpp @@ -0,0 +1,28 @@ +#include +#include +#include +#include +#include + +#include "Constants.h" +#include "MediaPlayerView.h" + +using namespace BPrivate; + +MediaPlayerView::MediaPlayerView(BRect viewFrame, BHandler *handler) + : BView(viewFrame, "mediaview", B_FOLLOW_ALL, B_FRAME_EVENTS|B_WILL_DRAW) +{ + fHandler = handler; + fMessenger = new BMessenger(handler); +} + +MediaPlayerView::~MediaPlayerView() +{ + delete fMessenger; +} + +void +MediaPlayerView::FrameResized(float width, float height) +{ + BView::FrameResized(width, height); +} diff --git a/src/apps/mediaplayer/MediaPlayerView.h b/src/apps/mediaplayer/MediaPlayerView.h new file mode 100644 index 0000000000..2ac34a99cc --- /dev/null +++ b/src/apps/mediaplayer/MediaPlayerView.h @@ -0,0 +1,19 @@ +#ifndef MEDIA_PLAYER_VIEW_H +#define MEDIA_PLAYER_VIEW_H + +#include +#include + +class MediaPlayerView : public BView { +public: + MediaPlayerView(BRect viewframe, BHandler *handler); + virtual ~MediaPlayerView(); + + virtual void FrameResized(float width, float height); + +private: + BHandler *fHandler; + BMessenger *fMessenger; +}; + +#endif // MEDIA_PLAYER_VIEW_H diff --git a/src/apps/mediaplayer/MediaPlayerWindow.cpp b/src/apps/mediaplayer/MediaPlayerWindow.cpp new file mode 100644 index 0000000000..03c3ac6d1a --- /dev/null +++ b/src/apps/mediaplayer/MediaPlayerWindow.cpp @@ -0,0 +1,180 @@ +#include +#include +#include +#include +#include +#include +#include + +#include "Constants.h" +#include "MediaPlayerApp.h" +#include "MediaPlayerView.h" +#include "MediaPlayerWindow.h" + +using namespace BPrivate; + +MediaPlayerWindow::MediaPlayerWindow(BRect frame) + : BWindow(frame,"Media Player",B_DOCUMENT_WINDOW,0) +{ + InitWindow(); + Show(); +} + +MediaPlayerWindow::MediaPlayerWindow(BRect frame, entry_ref *ref) + : BWindow(frame,"Media Player",B_DOCUMENT_WINDOW,0) +{ + InitWindow(); + OpenFile(ref); + Show(); +} + +MediaPlayerWindow::~MediaPlayerWindow() +{ +} + +void +MediaPlayerWindow::InitWindow() +{ + fMenuBar = new BMenuBar(BRect(0,0,0,0),"menubar"); + AddChild(fMenuBar); + + BRect viewFrame; + viewFrame = Bounds(); + viewFrame.top = fMenuBar->Bounds().Height()+1; // 021021 + viewFrame.left = 0; // 021021 + + fPlaverView = new MediaPlayerView(viewFrame, this); + fPlaverView->MakeFocus(true); + + BMenu * menu; + BMenuItem * menuItem; + + // File menu + fMenuBar->AddItem(menu = new BMenu("File")); + + fOpenFileMenu = new BMenu("Open File..."); + menu->AddItem(menuItem = new BMenuItem(fOpenFileMenu, new BMessage(MENU_OPEN_FILE))); + menuItem->SetShortcut('O',0); + fOpenURLMenu = new BMenu("Open URL..."); + menu->AddItem(menuItem = new BMenuItem(fOpenURLMenu, new BMessage(MENU_OPEN_URL))); + menuItem->SetShortcut('U',0); + menu->AddItem(fFileInfoItem = new BMenuItem("File Info...", new BMessage(MENU_FILE_INFO), 'I')); + fFileInfoItem->SetEnabled(false); + menu->AddSeparatorItem(); + + menu->AddItem(fCloseItem = new BMenuItem("Close", new BMessage(MENU_CLOSE), 'W')); + menu->AddItem(fQuitItem = new BMenuItem("Quit", new BMessage(MENU_QUIT), 'Q')); + + // View menu + fMenuBar->AddItem(menu = new BMenu("View")); + + menu->AddItem(fMiniModeItem = new BMenuItem("Mini mode", new BMessage(MENU_MINI_MODE), 'T')); + menu->AddItem(fHalfScaleItem = new BMenuItem("50% scale", new BMessage(MENU_HALF_SCALE), '0')); + fHalfScaleItem->SetEnabled(false); + menu->AddItem(fNormalScaleItem = new BMenuItem("100% scale", new BMessage(MENU_NORMAL_SCALE), '1')); + fNormalScaleItem->SetEnabled(false); + menu->AddItem(fDoubleScaleItem = new BMenuItem("200% scale", new BMessage(MENU_DOUBLE_SCALE), '2')); + fDoubleScaleItem->SetEnabled(false); + menu->AddItem(fFullScreenItem = new BMenuItem("Full screen", new BMessage(MENU_FULL_SCREEN), 'F')); + fFullScreenItem->SetEnabled(false); + + // Settings menu + fMenuBar->AddItem(menu = new BMenu("Settings")); + menu->AddItem(fApplicationPreferencesItem = new BMenuItem("Application Preferences...", + new BMessage(MENU_PREFERENCES))); + menu->AddItem(fLoopItem = new BMenuItem("Loop", new BMessage(MENU_LOOP), 'L')); + fLoopItem->SetEnabled(false); + menu->AddItem(fPreserveVideoTimingItem = new BMenuItem("Preserve Video Timing", + new BMessage(MENU_PRESERVE_VIDEO_TIMING))); + fPreserveVideoTimingItem->SetEnabled(false); + +} + +void +MediaPlayerWindow::MessageReceived(BMessage *message) +{ + if(message->WasDropped()) { + entry_ref ref; + if(message->FindRef("refs",0,&ref)==B_OK) { + message->what = B_REFS_RECEIVED; + be_app->PostMessage(message); + } + } + + switch(message->what){ + case MENU_CLOSE: { + if(this->QuitRequested()) { + BAutolock lock(this); + Quit(); + } + } + break; + case MENU_QUIT: + be_app->PostMessage(B_QUIT_REQUESTED); + break; + default: + BWindow::MessageReceived(message); + break; + } +} + +void +MediaPlayerWindow::MenusBeginning() +{ + // set up the recent documents menu + BMessage documents; + be_roster->GetRecentDocuments(&documents,9,NULL,APP_SIGNATURE); + + // delete old items.. + // shatty: it would be preferable to keep the old + // menu around instead of continuously thrashing + // the menu, but unfortunately there does not + // seem to be a straightforward way to update it + // going backwards may simplify memory management + for (int i = fOpenFileMenu->CountItems()-1 ; (i >= 0) ; i--) { + delete fOpenFileMenu->RemoveItem(i); + } + // add new items + int count = 0; + entry_ref ref; + while (documents.FindRef("refs",count++,&ref) == B_OK) { + if ((ref.device != -1) && (ref.directory != -1)) { + // sanity check passed + BMessage * openRecent = new BMessage(B_REFS_RECEIVED); + openRecent->AddRef("refs",&ref); + BMenuItem * item = new BMenuItem(ref.name,openRecent); + item->SetTarget(be_app); + fOpenFileMenu->AddItem(item); + } + } +} + +void +MediaPlayerWindow::Quit() +{ + media_player_app->CloseDocument(); + BWindow::Quit(); +} + +bool +MediaPlayerWindow::QuitRequested() +{ + return true; +} + +void +MediaPlayerWindow::OpenFile(entry_ref *ref) +{ + BFile file; + status_t fileinit; + + fileinit = file.SetTo(ref, B_READ_ONLY); + + if (fileinit == B_OK) { + // allocate media file etc. + } else { + // complain + } + + be_roster->AddToRecentDocuments(ref,APP_SIGNATURE); +} diff --git a/src/apps/mediaplayer/MediaPlayerWindow.h b/src/apps/mediaplayer/MediaPlayerWindow.h new file mode 100644 index 0000000000..416149ac6d --- /dev/null +++ b/src/apps/mediaplayer/MediaPlayerWindow.h @@ -0,0 +1,50 @@ +#ifndef MEDIA_PLAYER_WINDOW_H +#define MEDIA_PLAYER_WINDOW_H + +#include +#include +#include +#include +#include + +class MediaPlayerView; + +class MediaPlayerWindow + : public BWindow +{ +public: + MediaPlayerWindow(BRect frame); + MediaPlayerWindow(BRect frame, entry_ref *ref); + virtual ~MediaPlayerWindow(); + + virtual void Quit(); + virtual bool QuitRequested(); + virtual void MessageReceived(BMessage *message); + virtual void MenusBeginning(); + + void OpenFile(entry_ref *ref); + +private: + void InitWindow(); + + BMenuBar *fMenuBar; + BMenu *fOpenFileMenu; + BMenu *fOpenURLMenu; + BMenuItem *fFileInfoItem; + BMenuItem *fCloseItem; + BMenuItem *fQuitItem; + + BMenuItem *fMiniModeItem; + BMenuItem *fHalfScaleItem; + BMenuItem *fNormalScaleItem; + BMenuItem *fDoubleScaleItem; + BMenuItem *fFullScreenItem; + + BMenuItem *fApplicationPreferencesItem; + BMenuItem *fLoopItem; + BMenuItem *fPreserveVideoTimingItem; + + MediaPlayerView *fPlaverView; +}; + +#endif // MEDIA_PLAYER_WINDOW_H