/********************************************************************** Audacity: A Digital Audio Editor ToolsToolBar.cpp Dominic Mazzoni Shane T. Mueller Leland Lucius See ToolsToolBar.h for details *******************************************************************//*! \class ToolsToolBar \brief A kind of ToolBar with Tools on it. This class, which is a child of Toolbar, creates the window containing the tool selection (ibeam, envelope, move, zoom). The window can be embedded within a normal project window, or within a ToolbarFrame that is managed by a global ToolBarStub called gToolsToolBarStub. All of the controls in this window were custom-written for Audacity - they are not native controls on any platform - however, it is intended that the images could be easily replaced to allow "skinning" or just customization to match the look and feel of each platform. \see \ref Themability *//*******************************************************************/ #include "../Audacity.h" #include "ToolsToolBar.h" // For compilers that support precompilation, includes "wx/wx.h". #include #ifndef WX_PRECOMP #include #include #include #include #endif #include #include "MeterToolBar.h" #include "../Prefs.h" #include "../AllThemeResources.h" #include "../ImageManipulation.h" #include "../Project.h" #ifdef EXPERIMENTAL_SCRUBBING_BASIC #include "../TrackPanel.h" #endif #include "../Theme.h" #include "../widgets/AButton.h" #include "../Experimental.h" IMPLEMENT_CLASS(ToolsToolBar, ToolBar); //////////////////////////////////////////////////////////// /// Methods for ToolsToolBar //////////////////////////////////////////////////////////// BEGIN_EVENT_TABLE(ToolsToolBar, ToolBar) EVT_COMMAND_RANGE(firstTool, lastTool, wxEVT_COMMAND_BUTTON_CLICKED, ToolsToolBar::OnTool) END_EVENT_TABLE() //Standard constructor ToolsToolBar::ToolsToolBar() : ToolBar(ToolsBarID, _("Tools"), wxT("Tools")) { //Read the following wxASSERTs as documentating a design decision wxASSERT( selectTool == selectTool - firstTool ); wxASSERT( envelopeTool == envelopeTool - firstTool ); wxASSERT( slideTool == slideTool - firstTool ); wxASSERT( zoomTool == zoomTool - firstTool ); wxASSERT( drawTool == drawTool - firstTool ); wxASSERT( multiTool == multiTool - firstTool ); { #ifdef EXPERIMENTAL_SCRUBBING_BASIC mMessageOfTool[selectTool] = #if defined(__WXMAC__) _("Click and drag to select audio, Command-Click to scrub, Command-Double-Click to scroll-scrub, Command-drag to seek") #else _("Click and drag to select audio, Ctrl-Click to scrub, Ctrl-Double-Click to scroll-scrub, Ctrl-drag to seek") #endif ; #else mMessageOfTool[selectTool] = _("Click and drag to select audio"); #endif } mMessageOfTool[envelopeTool] = _("Click and drag to edit the amplitude envelope"); mMessageOfTool[drawTool] = _("Click and drag to edit the samples"); #if defined( __WXMAC__ ) mMessageOfTool[zoomTool] = _("Click to Zoom In, Shift-Click to Zoom Out"); #elif defined( __WXMSW__ ) mMessageOfTool[zoomTool] = _("Drag to Zoom Into Region, Right-Click to Zoom Out"); #elif defined( __WXGTK__ ) mMessageOfTool[zoomTool] = _("Left=Zoom In, Right=Zoom Out, Middle=Normal"); #endif mMessageOfTool[slideTool] = _("Click and drag to move a track in time"); mMessageOfTool[multiTool] = wxT(""); // multi-mode tool bool multiToolActive = false; gPrefs->Read(wxT("/GUI/ToolBars/Tools/MultiToolActive"), &multiToolActive); if (multiToolActive) mCurrentTool = multiTool; else mCurrentTool = selectTool; } ToolsToolBar::~ToolsToolBar() { } void ToolsToolBar::RegenerateToolsTooltips() { // JKC: // Under Win98 Tooltips appear to be buggy, when you have a lot of // tooltip messages flying around. I found that just creating a // twelfth tooltip caused Audacity to crash when it tried to show // any tooltip. // // Win98 does NOT recover from this crash - for any application which is // using tooltips will also crash thereafter... so you must reboot. // Rather weird. // // Getting windows to process more of its stacked up messages seems // to workaround the problem. The problem is not fully understood though // (as of April 2003). // Vaughan, October 2003: Now we're crashing on Win2K if // "Quit when closing last window" is unchecked, when we come back // through here, on either of the wxSafeYield calls. // James confirms that commenting them out does not cause his original problem // to reappear, so they're commented out now. // wxSafeYield(); //Deal with some queued up messages... #if wxUSE_TOOLTIPS mTool[selectTool]->SetToolTip(_("Selection Tool")); mTool[envelopeTool]->SetToolTip(_("Envelope Tool")); mTool[slideTool]->SetToolTip(_("Time Shift Tool")); mTool[zoomTool]->SetToolTip(_("Zoom Tool")); mTool[drawTool]->SetToolTip(_("Draw Tool")); mTool[multiTool]->SetToolTip(_("Multi-Tool Mode")); #endif // wxSafeYield(); return; } void ToolsToolBar::UpdatePrefs() { RegenerateToolsTooltips(); } AButton * ToolsToolBar::MakeTool( teBmps eTool, int id, const wxChar *label) { AButton *button = ToolBar::MakeButton( bmpRecoloredUpSmall, bmpRecoloredDownSmall, bmpRecoloredHiliteSmall, eTool, eTool, eTool, wxWindowID(id), wxDefaultPosition, true, theTheme.ImageSize( bmpRecoloredUpSmall )); button->SetLabel( label ); mToolSizer->Add( button ); return button; } void ToolsToolBar::Populate() { MakeButtonBackgroundsSmall(); Add(mToolSizer = safenew wxGridSizer(2, 3, 1, 1)); /* Tools */ mTool[ selectTool ] = MakeTool( bmpIBeam, selectTool, _("Selection Tool") ); mTool[ envelopeTool ] = MakeTool( bmpEnvelope, envelopeTool, _("Envelope Tool") ); mTool[ drawTool ] = MakeTool( bmpDraw, drawTool, _("Draw Tool") ); mTool[ zoomTool ] = MakeTool( bmpZoom, zoomTool, _("Zoom Tool") ); mTool[ slideTool ] = MakeTool( bmpTimeShift, slideTool, _("Slide Tool") ); mTool[ multiTool ] = MakeTool( bmpMulti, multiTool, _("Multi Tool") ); mTool[mCurrentTool]->PushDown(); RegenerateToolsTooltips(); } /// Gets the currently active tool /// In Multi-mode this might not return the multi-tool itself /// since the active tool may be changed by what you hover over. int ToolsToolBar::GetCurrentTool() { return mCurrentTool; } /// Sets the currently active tool /// @param tool - The index of the tool to be used. /// @param show - should we update the button display? void ToolsToolBar::SetCurrentTool(int tool, bool show) { //In multi-mode the current tool is shown by the //cursor icon. The buttons are not updated. #ifdef EXPERIMENTAL_SCRUBBING_BASIC if (tool != selectTool) { AudacityProject *p = GetActiveProject(); if (p) { TrackPanel *tp = p->GetTrackPanel(); if (tp) { tp->StopScrubbing(); } } } #endif bool leavingMulticlipMode = IsDown(multiTool) && show && tool != multiTool; if (leavingMulticlipMode) mTool[multiTool]->PopUp(); if (tool != mCurrentTool || leavingMulticlipMode) { if (show) mTool[mCurrentTool]->PopUp(); mCurrentTool=tool; if (show) mTool[mCurrentTool]->PushDown(); } //JKC: ANSWER-ME: Why is this RedrawAllProjects() line required? //msmeyer: I think it isn't, we leave it out for 1.3.1 (beta), and // we'll see if anyone complains. // RedrawAllProjects(); //msmeyer: But we instruct the projects to handle the cursor shape again if (show) { RefreshCursorForAllProjects(); gPrefs->Write(wxT("/GUI/ToolBars/Tools/MultiToolActive"), IsDown(multiTool)); gPrefs->Flush(); } } bool ToolsToolBar::IsDown(int tool) { return mTool[tool]->IsDown(); } int ToolsToolBar::GetDownTool() { int tool; for (tool = firstTool; tool <= lastTool; tool++) if (IsDown(tool)) return tool; return firstTool; // Should never happen } const wxChar * ToolsToolBar::GetMessageForTool( int ToolNumber ) { wxASSERT( ToolNumber >= 0 ); wxASSERT( ToolNumber < numTools ); return mMessageOfTool[ToolNumber]; } void ToolsToolBar::OnTool(wxCommandEvent & evt) { mCurrentTool = evt.GetId() - firstTool; for (int i = 0; i < numTools; i++) if (i == mCurrentTool) mTool[i]->PushDown(); else mTool[i]->PopUp(); #ifdef EXPERIMENTAL_SCRUBBING_BASIC if (0 != mCurrentTool) { AudacityProject *p = GetActiveProject(); if (p) { TrackPanel *tp = p->GetTrackPanel(); if (tp) { tp->StopScrubbing(); } } } #endif RedrawAllProjects(); gPrefs->Write(wxT("/GUI/ToolBars/Tools/MultiToolActive"), IsDown(multiTool)); gPrefs->Flush(); }