[haiku-commits] r37109 - in haiku/trunk/src/tests/kits/interface: . menu menu/menuworld

  • From: stefano.ceccherini@xxxxxxxxx
  • To: haiku-commits@xxxxxxxxxxxxx
  • Date: Sat, 12 Jun 2010 09:03:01 +0200 (CEST)

Author: jackburton
Date: 2010-06-12 09:03:01 +0200 (Sat, 12 Jun 2010)
New Revision: 37109
Changeset: http://dev.haiku-os.org/changeset/37109/haiku

Added:
   haiku/trunk/src/tests/kits/interface/menu/
   haiku/trunk/src/tests/kits/interface/menu/menuworld/
   haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/Jamfile
   haiku/trunk/src/tests/kits/interface/menu/menuworld/LICENSE
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuWindow.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuWindow.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuWorld.rsrc
   haiku/trunk/src/tests/kits/interface/menu/menuworld/PostDispatchInvoker.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/PostDispatchInvoker.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/TestIcons.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/TestMenuBuilder.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/TestMenuBuilder.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/ViewLayoutFactory.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/ViewLayoutFactory.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/_README.txt
   haiku/trunk/src/tests/kits/interface/menu/menuworld/constants.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/constants.h
   haiku/trunk/src/tests/kits/interface/menu/menuworld/main.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/stddlg.cpp
   haiku/trunk/src/tests/kits/interface/menu/menuworld/stddlg.h
Log:
Imported MenuWorld beos sample code into the repository.
Wrote a jamfile and did some build fix (but doesn't build yet).


Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.cpp
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.cpp      
                        (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.cpp      
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,79 @@
+//--------------------------------------------------------------------
+//     
+//     BitmapMenuItem.cpp
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#include "BitmapMenuItem.h"
+#include "constants.h"
+
+//====================================================================
+//     BitmapMenuItem Implementation
+
+
+
+//--------------------------------------------------------------------
+//     BitmapMenuItem constructors, destructors, operators
+
+BitmapMenuItem::BitmapMenuItem(const char* name, const BBitmap& bitmap,
+       BMessage* message, char shortcut, uint32 modifiers)
+       : BMenuItem(name, message, shortcut, modifiers),
+       m_bitmap(bitmap.Bounds(), bitmap.ColorSpace())
+{
+       // Sadly, operator= for bitmaps is not yet implemented.
+       // Half of m_bitmap's initialization is above; now we copy
+       // the bits.
+       m_bitmap.SetBits(bitmap.Bits(), bitmap.BitsLength(),
+               0, bitmap.ColorSpace());
+}
+
+
+
+//--------------------------------------------------------------------
+//     BitmapMenuItem constructors, destructors, operators
+
+void BitmapMenuItem::Draw(void)
+{
+       BMenu* menu = Menu();
+       if (menu) {
+               BRect itemFrame = Frame();
+               BRect bitmapFrame = itemFrame;
+               bitmapFrame.InsetBy(2, 2); // account for 2-pixel margin
+               
+               menu->SetDrawingMode(B_OP_COPY);
+               menu->SetHighColor(BKG_GREY);
+               menu->FillRect(itemFrame);
+               menu->DrawBitmap(&m_bitmap, bitmapFrame);
+               
+               if (IsSelected()) {
+                       // a nonstandard but simple way to draw highlights
+                       menu->SetDrawingMode(B_OP_INVERT);
+                       menu->SetHighColor(0,0,0);
+                       menu->FillRect(itemFrame);
+               }
+       }
+}
+
+void BitmapMenuItem::GetContentSize(float* width, float* height)
+{
+       GetBitmapSize(width, height);
+}
+
+
+
+//--------------------------------------------------------------------
+//     BitmapMenuItem accessors
+
+void BitmapMenuItem::GetBitmapSize(float* width, float* height)
+{
+       BRect r = m_bitmap.Bounds();
+       *width = r.Width() + 4; // 2-pixel boundary on either side
+       *height = r.Height() + 4; // 2-pixel boundary on top/bottom
+}

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.h
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.h        
                        (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/BitmapMenuItem.h        
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,54 @@
+//--------------------------------------------------------------------
+//     
+//     BitmapMenuItem.h
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#ifndef _BitmapMenuItem_h
+#define _BitmapMenuItem_h
+
+#include <Bitmap.h>
+#include <MenuItem.h>
+
+//====================================================================
+//     CLASS: BitmapMenuItem
+
+class BitmapMenuItem : public BMenuItem
+{
+       //----------------------------------------------------------------
+       //      Constructors, destructors, operators
+
+public:
+                                       BitmapMenuItem(const char* name, const 
BBitmap& bitmap,
+                                               BMessage* message, char 
shortcut = 0,
+                                               uint32 modifiers = 0);
+                               
+                               
+       //----------------------------------------------------------------
+       //      Virtual member function overrides
+
+protected:     
+       void                            Draw(void);
+       void                            GetContentSize(float* width, float* 
height);
+
+       //----------------------------------------------------------------
+       //      Accessors
+
+public:
+       void                            GetBitmapSize(float* width, float* 
height);
+       
+       //----------------------------------------------------------------
+       //      Member variables
+       
+private:
+       BBitmap m_bitmap;       
+};
+
+#endif /* _BitmapMenuItem_h */
\ No newline at end of file

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/Jamfile
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/Jamfile                 
        (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/Jamfile 2010-06-12 
07:03:01 UTC (rev 37109)
@@ -0,0 +1,15 @@
+SubDir HAIKU_TOP src tests kits interface menu menuworld ;
+
+Application MenuWorld :
+       BitmapMenuItem.cpp
+       constants.cpp
+       main.cpp
+       MenuApp.cpp
+       MenuView.cpp
+       MenuWindow.cpp
+       PostDispatchInvoker.cpp
+       stddlg.cpp
+       TestMenuBuilder.cpp
+       ViewLayoutFactory.cpp
+       : be $(TARGET_LIBSUPC++)
+       ;

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/LICENSE
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/LICENSE                 
        (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/LICENSE 2010-06-12 
07:03:01 UTC (rev 37109)
@@ -0,0 +1,31 @@
+----------------------
+Be Sample Code License
+----------------------
+
+Copyright 1991-1999, Be Incorporated.
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+
+1. Redistributions of source code must retain the above copyright
+   notice, this list of conditions, and the following disclaimer.
+
+2. Redistributions in binary form must reproduce the above copyright
+   notice, this list of conditions, and the following disclaimer in the
+   documentation and/or other materials provided with the distribution.
+
+3. The name of the author may not be used to endorse or promote products
+   derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR
+IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+OF TITLE, NON-INFRINGEMENT, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
+TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.    

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.cpp
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.cpp             
                (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.cpp     
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,50 @@
+//--------------------------------------------------------------------
+//     
+//     MenuApp.cpp
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#include <Alert.h>
+
+#include "constants.h"
+#include "MenuApp.h"
+#include "MenuWindow.h"
+
+//====================================================================
+//     MenuApp Implementation
+
+
+
+//--------------------------------------------------------------------
+//     MenuApp constructors, destructors, operators
+
+MenuApp::MenuApp()
+       : BApplication(STR_APP_SIG)
+{
+       // empty
+}
+
+
+
+//--------------------------------------------------------------------
+//     MenuApp virtual function overrides
+
+void MenuApp::AboutRequested(void)
+{
+       BAlert* aboutBox = new BAlert(STR_ABOUT_TITLE,
+               STR_ABOUT_DESC, STR_ABOUT_BUTTON);
+       aboutBox->Go(); 
+}
+
+void MenuApp::ReadyToRun(void)
+{
+       MenuWindow* pWin = new MenuWindow(STR_APP_NAME);
+       pWin->Show();
+}

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.h
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.h               
                (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuApp.h       
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,39 @@
+//--------------------------------------------------------------------
+//     
+//     MenuApp.h
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#ifndef _MenuApp_h
+#define _MenuApp_h
+
+#include <Application.h>
+
+//====================================================================
+//     CLASS: MenuApp
+
+class MenuApp : public BApplication
+{
+       //----------------------------------------------------------------
+       //      Constructors, destructors, operators
+
+public:
+                               MenuApp();
+       
+       //----------------------------------------------------------------
+       //      Virtual function overrides
+
+public:
+       void            AboutRequested(void);   
+       void            ReadyToRun(void);
+       
+};
+
+#endif /* _MenuApp_h */
\ No newline at end of file

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.cpp
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.cpp            
                (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.cpp    
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,563 @@
+//--------------------------------------------------------------------
+//     
+//     MenuView.cpp
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#include <Alert.h>
+#include <Button.h>
+#include <CheckBox.h>
+#include <Menu.h>
+#include <MenuItem.h>
+#include <OutlineListView.h>
+#include <ScrollView.h>
+#include <TextControl.h>
+#include <List.h>
+#include <string.h>
+
+#include "constants.h"
+#include "MenuView.h"
+#include "MenuWindow.h"
+#include "PostDispatchInvoker.h"
+#include "stddlg.h"
+#include "ViewLayoutFactory.h"
+
+
+//====================================================================
+//     MenuView Implementation
+
+
+//--------------------------------------------------------------------
+//     MenuView constructors, destructors, operators
+
+MenuView::MenuView(uint32 resizingMode)
+       : BView(BRect(0, 0, 0, 0), "Menu View", resizingMode,
+               B_WILL_DRAW)
+{
+       ViewLayoutFactory aFactory; // for semi-intelligent layout
+       
+       SetViewColor(BKG_GREY);
+
+       // "hide user menus" check box
+       float fCheck_x = 20.0f;
+       float fCheck_y = 100.0f;
+       m_pHideUserCheck = aFactory.MakeCheckBox("Hide User Menus",
+               STR_HIDE_USER_MENUS, MSG_WIN_HIDE_USER_MENUS,
+               BPoint(fCheck_x, fCheck_y));
+       m_pHideUserCheck->SetValue(B_CONTROL_OFF);
+       AddChild(m_pHideUserCheck);
+       
+       // "large test icons" check box
+       fCheck_y = m_pHideUserCheck->Frame().bottom + 10;
+       m_pLargeTestIconCheck = aFactory.MakeCheckBox("Large Test Icons",
+               STR_LARGE_TEST_ICONS, MSG_WIN_LARGE_TEST_ICONS,
+               BPoint(fCheck_x, fCheck_y));
+       m_pLargeTestIconCheck->SetValue(B_CONTROL_OFF);
+       AddChild(m_pLargeTestIconCheck);
+       
+       // "add menu", "add item", "delete" buttons
+       BList buttons;
+       float fButton_x = m_pHideUserCheck->Frame().right + 15;
+       float fButton_y = m_pHideUserCheck->Frame().top;
+       
+       m_pAddMenuButton = aFactory.MakeButton("Add Menu Bar", STR_ADD_MENU,
+               MSG_VIEW_ADD_MENU, BPoint(fButton_x, fButton_y));
+       AddChild(m_pAddMenuButton);
+       buttons.AddItem(m_pAddMenuButton);
+       
+       // for purposes of size calculation, use the longest piece
+       // of text we're going to stuff into the button
+       const char* addItemText;
+       float itemLen, sepLen;
+       itemLen = be_plain_font->StringWidth(STR_ADD_ITEM);
+       sepLen = be_plain_font->StringWidth(STR_ADD_SEP);
+       addItemText = (itemLen > sepLen) ? STR_ADD_ITEM : STR_ADD_SEP;
+       m_pAddItemButton = aFactory.MakeButton("Add Item To Menu",
+               addItemText, MSG_VIEW_ADD_ITEM,
+               BPoint(fButton_x, fButton_y));
+       m_pAddItemButton->SetEnabled(false);
+       AddChild(m_pAddItemButton);
+       buttons.AddItem(m_pAddItemButton);
+       
+       m_pDelButton = aFactory.MakeButton("Delete Menu Bar", STR_DELETE_MENU,
+               MSG_VIEW_DELETE_MENU, BPoint(fButton_x, fButton_y));
+       m_pDelButton->SetEnabled(false);
+       AddChild(m_pDelButton);
+       buttons.AddItem(m_pDelButton);
+       
+       // now resize list of buttons to max width
+       aFactory.ResizeToListMax(buttons, RECT_WIDTH);
+       
+       // now align buttons along left side
+       aFactory.Align(buttons, ALIGN_LEFT,
+               m_pAddItemButton->Frame().Height() + 15);
+               
+       // now make add menu the default, AFTER we've
+       // laid out the buttons, since the button bloats
+       // when it's the default
+       m_pAddMenuButton->MakeDefault(true);
+
+       // item "label" control
+       float fEdit_left = 20.0f, fEdit_bottom = m_pHideUserCheck->Frame().top 
- 20;
+       float fEdit_right = m_pAddItemButton->Frame().right;
+       
+       m_pLabelCtrl = aFactory.MakeTextControl("Menu Bar Control",
+               STR_LABEL_CTRL, NULL, BPoint(fEdit_left, fEdit_bottom),
+               fEdit_right - fEdit_left, CORNER_BOTTOMLEFT);
+       AddChild(m_pLabelCtrl);
+       
+       // menu outline view
+       BRect r;
+       r.left = m_pAddItemButton->Frame().right + 30;
+       r.top = 20.0f;
+       r.right = r.left + 200 - B_V_SCROLL_BAR_WIDTH;
+       // API quirk here: <= 12 (hscroll height - 2) height
+       // results in scrollbar drawing error
+       r.bottom = r.top + 100 - B_H_SCROLL_BAR_HEIGHT;
+
+       m_pMenuOutlineView = new BOutlineListView(r, "Menu Outline",
+               B_SINGLE_SELECTION_LIST, B_FOLLOW_ALL);
+       m_pMenuOutlineView->SetSelectionMessage(
+               new BMessage(MSG_MENU_OUTLINE_SEL));
+       
+       // wrap outline view in scroller
+       m_pScrollView = new BScrollView("Menu Outline Scroller",
+               m_pMenuOutlineView, B_FOLLOW_LEFT | B_FOLLOW_TOP, 0,
+               true, true);
+       m_pScrollView->SetViewColor(BKG_GREY);
+       AddChild(m_pScrollView);
+       
+}
+
+
+
+//--------------------------------------------------------------------
+//     MenuView virtual function overrides
+
+void MenuView::MessageReceived(BMessage* message)
+{
+       switch (message->what) {
+       case MSG_VIEW_ADD_MENU:
+               AddMenu(message);
+               break;
+       case MSG_VIEW_DELETE_MENU:
+               DeleteMenu(message);
+               break;
+       case MSG_VIEW_ADD_ITEM:
+               AddMenuItem(message);
+               break;
+       case MSG_MENU_OUTLINE_SEL:
+               MenuSelectionChanged(message);
+               break;
+       case MSG_LABEL_EDIT:
+               SetButtonState();
+               break;
+       default:
+               BView::MessageReceived(message);
+               break;
+       }
+}
+
+void MenuView::AllAttached(void)
+{
+       if (! Valid()) {
+               return;
+       }
+
+       // Set button and view targets (now that window looper is available).
+       m_pAddMenuButton->SetTarget(this);
+       m_pDelButton->SetTarget(this);
+       m_pAddItemButton->SetTarget(this);
+       m_pMenuOutlineView->SetTarget(this);
+       
+       // Set button's initial state
+       SetButtonState();
+       
+       // Wrap a message filter/invoker around the label control's text field
+       // that will post us B_LABEL_EDIT msg after the text field processes a
+       // B_KEY_DOWN message.
+       m_pLabelCtrl->TextView()->AddFilter(
+               new PostDispatchInvoker(B_KEY_DOWN, new 
BMessage(MSG_LABEL_EDIT), this));
+       
+       // Get one item's height by adding a dummy item to
+       // the BOutlineListView and calculating its height.
+       m_pMenuOutlineView->AddItem(new BStringItem("Dummy"));
+       float itemHeight = m_pMenuOutlineView->ItemFrame(0).Height();
+       itemHeight++;   // account for 1-pixel offset between items
+                                       // which eliminates overlap
+       delete m_pMenuOutlineView->RemoveItem((int32)0);
+       
+       // Resize outline list view to integral item height.
+       // fudge factor of 4 comes from 2-pixel space between
+       // scrollview and outline list view on top & bottom
+       float viewHeight = 16*itemHeight;
+       m_pScrollView->ResizeTo(m_pScrollView->Frame().Width(),
+               viewHeight + B_H_SCROLL_BAR_HEIGHT + 4);
+       BScrollBar *pBar = m_pScrollView->ScrollBar(B_HORIZONTAL);
+       if (pBar) {
+               pBar->SetRange(0, 300);
+       }
+       
+       // Resize view to surround contents.
+       ViewLayoutFactory aFactory;
+       aFactory.ResizeAroundChildren(*this, BPoint(20,20));    
+}
+
+
+
+//--------------------------------------------------------------------
+//     MenuView operations
+
+void MenuView::PopulateUserMenu(BMenu* pMenu, int32 index)
+{
+       if ((! pMenu) || (! Valid())) {
+               return;
+       }
+               
+       // blow away all menu items
+       BMenuItem* pMenuItem = pMenu->RemoveItem((int32)0);
+       while(pMenuItem) {
+               delete pMenuItem;
+               pMenuItem = pMenu->RemoveItem((int32)0);
+       }
+       
+       // build menu up from outline list view 
+       BListItem* pListItem = m_pMenuOutlineView->ItemUnderAt(NULL, true, 
index);
+       
+       // recursive buildup of menu items
+       BuildMenuItems(pMenu, pListItem, m_pMenuOutlineView);
+}
+
+
+
+//--------------------------------------------------------------------
+//     MenuView message handlers
+
+void MenuView::AddMenu(BMessage* message)
+{
+       if (! Valid()) {
+               return;
+       }
+       
+       const char* menuName = m_pLabelCtrl->Text();
+       if ((! menuName) || (! *menuName)) {
+               BAlert* pAlert = new BAlert("Add menu alert",
+                       "Please specify the menu name first.", "OK");
+               pAlert->Go();
+               return;
+       }
+       
+       m_pMenuOutlineView->AddItem(new BStringItem(menuName)); 
+       
+       // add some info and pass to window
+       BMessage newMsg(MSG_WIN_ADD_MENU);
+       newMsg.AddString("Menu Name", menuName);
+       BWindow* pWin = Window();
+       if (pWin) {
+               pWin->PostMessage(&newMsg);
+       }
+       
+       // Reset the label control and buttons
+       m_pLabelCtrl->SetText("");
+       SetButtonState();
+}
+
+void MenuView::DeleteMenu(BMessage* message)
+{
+       if (! Valid())
+               return;
+
+       int32 itemCount;        
+       int32 selected = m_pMenuOutlineView->CurrentSelection();
+       if (selected < 0)
+               return;
+       
+       BStringItem* pSelItem = dynamic_cast<BStringItem*>
+               (m_pMenuOutlineView->ItemAt(selected));
+       if (! pSelItem)
+               return;
+       
+       if (pSelItem->OutlineLevel() == 0) {
+               // get index of item among items in 0 level
+               itemCount = m_pMenuOutlineView->CountItemsUnder(NULL, true);
+               int32 i;
+               for (i=0; i<itemCount; i++) {
+                       BListItem* pItem = 
m_pMenuOutlineView->ItemUnderAt(NULL, true, i);
+                       if (pItem == pSelItem) {
+                               break;
+                       }
+               }
+               
+               // Stuff the index into the message and pass along to
+               // the window.
+               BMessage newMsg(MSG_WIN_DELETE_MENU);
+               newMsg.AddInt32("Menu Index", i);
+               BWindow* pWin = Window();
+               if (pWin) {
+                       pWin->PostMessage(&newMsg);
+               }
+       }                       
+                               
+       // Find & record all subitems of selection, because we'll
+       // have to delete them after they're removed from the list.
+       BList subItems;
+       int32 j;
+       itemCount = m_pMenuOutlineView->CountItemsUnder(pSelItem, false);
+       for (j=0; j<itemCount; j++) {
+               BListItem* pItem = m_pMenuOutlineView->ItemUnderAt(pSelItem, 
false, j);
+               subItems.AddItem(pItem);
+       }
+       
+       // Note the superitem for reference just below
+       BStringItem* pSuperitem = dynamic_cast<BStringItem*>
+               (m_pMenuOutlineView->Superitem(pSelItem));
+               
+       // Remove selected item and all subitems from
+       // the outline list view.
+       m_pMenuOutlineView->RemoveItem(pSelItem); // removes super- and subitems
+       
+       // Update window status
+       MenuWindow* pWin = dynamic_cast<MenuWindow*>(Window());
+       if (pWin) {
+               const char* itemName = pSelItem->Text();
+               if (strcmp(itemName, STR_SEPARATOR)) {
+                       pWin->UpdateStatus(STR_STATUS_DELETE_ITEM, itemName);
+               } else {
+                       pWin->UpdateStatus(STR_STATUS_DELETE_SEPARATOR);
+               }
+       }
+
+       // Delete the selected item and all subitems    
+       for (j=0; j<itemCount; j++) {
+               BListItem* pItem = 
reinterpret_cast<BListItem*>(subItems.ItemAt(j));
+               delete pItem; // deletes subitems
+       }
+       delete pSelItem; // deletes superitem
+       
+       if (pSuperitem) {
+               // There's a bug in outline list view which does not
+               // update the superitem correctly. The only way to do so
+               // is to remove and add a brand-new superitem afresh.
+               if (! m_pMenuOutlineView->CountItemsUnder(pSuperitem, true))
+               {
+                       int32 index = 
m_pMenuOutlineView->FullListIndexOf(pSuperitem);
+                       m_pMenuOutlineView->RemoveItem(pSuperitem);
+                       BStringItem* pCloneItem = new BStringItem(
+                               pSuperitem->Text(), pSuperitem->OutlineLevel());
+                       m_pMenuOutlineView->AddItem(pCloneItem, index);
+                       delete pSuperitem;
+               }
+       }
+}
+
+void MenuView::AddMenuItem(BMessage* message)
+{
+       if (! Valid()) {
+               return;
+       }               
+       
+       // Add item to outline list view but DON'T update the
+       // window right away; the actual menu items will be
+       // created dynamically later on.
+       int32 selected = m_pMenuOutlineView->CurrentSelection();
+       if (selected >= 0) {
+               BListItem* pSelItem = m_pMenuOutlineView->ItemAt(selected);
+               if (pSelItem) {         
+
+                       int32 level = pSelItem->OutlineLevel() + 1;
+                       int32 index = 
m_pMenuOutlineView->FullListIndexOf(pSelItem)
+                               + m_pMenuOutlineView->CountItemsUnder(pSelItem, 
false) + 1;
+                       const char* itemName = m_pLabelCtrl->Text();
+                       bool bIsSeparator = IsSeparator(itemName);
+
+                       if (bIsSeparator) {
+                               m_pMenuOutlineView->AddItem(new 
BStringItem(STR_SEPARATOR, level),
+                                       index);
+                       } else {
+                               m_pMenuOutlineView->AddItem(new 
BStringItem(itemName, level),
+                                       index);
+                       }
+
+                       MenuWindow* pWin = dynamic_cast<MenuWindow*>(Window());
+                       if (pWin) {
+                               if (! bIsSeparator) {
+                                       pWin->UpdateStatus(STR_STATUS_ADD_ITEM, 
itemName);
+                               } else {
+                                       
pWin->UpdateStatus(STR_STATUS_ADD_SEPARATOR);
+                               }
+                       }
+
+                       m_pMenuOutlineView->Invalidate();       // outline view 
doesn't
+                                                                               
                // invalidate correctly
+                       
+                       // Reset the label control the buttons
+                       m_pLabelCtrl->SetText("");
+                       SetButtonState();
+               }
+       }       
+}
+
+void MenuView::MenuSelectionChanged(BMessage* message)
+{
+       SetButtonState();
+}
+
+
+
+//--------------------------------------------------------------------
+//     MenuView implementation member functions
+
+void MenuView::BuildMenuItems(BMenu* pMenu, BListItem* pSuperitem,
+       BOutlineListView* pView)
+{
+       if ((! pMenu) || (! pSuperitem) || (! pView)) {
+               return;
+       }
+       
+       int32 len = pView->CountItemsUnder(pSuperitem, true);
+       if (len == 0) {
+               BMenuItem* pEmptyItem = new BMenuItem(STR_MNU_EMPTY_ITEM, NULL);
+               pEmptyItem->SetEnabled(false);
+               pMenu->AddItem(pEmptyItem);
+       }
+       
+       for (int32 i=0; i<len; i++) {
+               BStringItem* pItem = dynamic_cast<BStringItem*>
+                       (pView->ItemUnderAt(pSuperitem, true, i));
+               if (pItem) {
+                       if (pView->CountItemsUnder(pItem, true) > 0) {
+                               // add a submenu & fill it
+                               BMenu* pNewMenu = new BMenu(pItem->Text());
+                               BuildMenuItems(pNewMenu, pItem, pView);
+                               pMenu->AddItem(pNewMenu);
+                       } else {
+                               if (strcmp(pItem->Text(), STR_SEPARATOR)) {
+                                       // add a string item
+                                       BMessage* pMsg = new 
BMessage(MSG_USER_ITEM);
+                                       pMsg->AddString("Item Name", 
pItem->Text());
+                                       pMenu->AddItem(new 
BMenuItem(pItem->Text(), pMsg));
+                               } else {
+                                       // add a separator item
+                                       pMenu->AddItem(new BSeparatorItem());
+                               }
+                       }
+               }
+       }
+}
+
+bool MenuView::IsSeparator(const char* text) const
+{
+       if (! text) {
+               return true;
+       }
+       
+       if (! *text) {
+               return true;
+       }
+       
+       int32 len = strlen(text);
+       for (int32 i = 0; i < len; i++) {
+               char ch = text[i];
+               if ((ch != ' ') && (ch != '-')) {
+                       return false;
+               }
+       }
+       
+       return true;
+}
+
+void MenuView::SetButtonState(void)
+{
+       if (! Valid()) {
+               return;
+       }
+
+       // See if an item in the outline list is selected
+       int32 index = m_pMenuOutlineView->CurrentSelection();
+       bool bIsSelected = (index >= 0);
+       
+       // If an item is selected, see if the selected
+       // item is a separator
+       bool bSeparatorSelected = false;
+       if (bIsSelected) {
+               BStringItem* pItem = dynamic_cast<BStringItem*>
+                       (m_pMenuOutlineView->ItemAt(index));
+               if (pItem) {
+                       bSeparatorSelected = (! strcmp(pItem->Text(), 
STR_SEPARATOR));
+               }
+       }
+
+       // Delete: enable if anything is selected
+       m_pDelButton->SetEnabled(bIsSelected);
+       
+       // Add Item: enable if anything but a separator is selected     
+       bool bEnableAddItem = bIsSelected && (! bSeparatorSelected);
+       m_pAddItemButton->SetEnabled(bEnableAddItem);
+
+       // Add Menu: enable if there's any text in the label field
+       const char* labelText = m_pLabelCtrl->Text();
+       m_pAddMenuButton->SetEnabled(labelText && (*labelText));
+               
+       // Add Item: text says Add Separator if button is enabled
+       // and the label field contains separator text,
+       // Add Item otherwise
+       const char* itemText;
+       if (bEnableAddItem && IsSeparator(labelText)) {
+               itemText = STR_ADD_SEP;
+       } else {
+               itemText = STR_ADD_ITEM;
+       }
+       m_pAddItemButton->SetLabel(itemText);
+
+       // If add item button is enabled, it should be the default      
+       if (bEnableAddItem) {
+               m_pAddItemButton->MakeDefault(true);
+       } else {
+               m_pAddMenuButton->MakeDefault(true);
+       }
+}
+
+bool MenuView::Valid(void)
+{
+       if (! m_pLabelCtrl) {
+               ierror(STR_NO_LABEL_CTRL);
+               return false;
+       }
+       if (! m_pHideUserCheck) {
+               ierror(STR_NO_HIDE_USER_CHECK);
+               return false;
+       }
+       if (! m_pLargeTestIconCheck) {
+               ierror(STR_NO_LARGE_ICON_CHECK);
+               return false;
+       }
+       if (! m_pAddMenuButton) {
+               ierror(STR_NO_ADDMENU_BUTTON);
+               return false;
+       }
+       if (! m_pAddItemButton) {
+               ierror(STR_NO_ADDITEM_BUTTON);
+               return false;
+       }
+       if (! m_pDelButton) {
+               ierror(STR_NO_DELETE_BUTTON);
+               return false;
+       }
+       if (! m_pMenuOutlineView) {
+               ierror(STR_NO_MENU_OUTLINE);
+               return false;
+       }
+       if (! m_pScrollView) {
+               ierror(STR_NO_MENU_SCROLL_VIEW);
+               return false;
+       }
+       return true;            
+}
+

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.h
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.h              
                (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuView.h      
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,85 @@
+//--------------------------------------------------------------------
+//     
+//     MenuView.h
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#ifndef _MenuView_h
+#define _MenuView_h
+
+
+#include <View.h>
+
+class BButton;
+class BListItem;
+class BOutlineListView;
+class BStringView;
+class BTextControl;
+//====================================================================
+//     CLASS: MenuView
+
+class MenuView : public BView
+{
+       //----------------------------------------------------------------
+       //      Constructors, destructors, operators
+
+public:
+                                       MenuView(uint32 resizingMode);
+                               
+                               
+       //----------------------------------------------------------------
+       //      Virtual member function overrides
+
+public:        
+       void                            MessageReceived(BMessage* message);
+       void                            AllAttached(void);
+       
+
+       //----------------------------------------------------------------
+       //      Operations
+public:
+       void                            PopulateUserMenu(BMenu* pMenu, int32 
index);
+
+       //----------------------------------------------------------------
+       //      Message handlers
+
+private:
+       void                            AddMenu(BMessage* message);
+       void                            DeleteMenu(BMessage* message);
+       void                            AddMenuItem(BMessage* message);
+       void                            MenuSelectionChanged(BMessage* message);
+       
+       
+       //----------------------------------------------------------------
+       //      Implementation member functions
+       
+private:
+       void                            BuildMenuItems(BMenu* pMenu, BListItem* 
superitem,
+                                                       BOutlineListView* 
pView);
+       bool                            IsSeparator(const char* text) const;
+       void                            SetButtonState(void);
+       bool                            Valid(void);
+       
+
+       //----------------------------------------------------------------
+       //      Member variables
+       
+private:
+       BTextControl*           m_pLabelCtrl;
+       BCheckBox*                      m_pHideUserCheck;
+       BCheckBox*                      m_pLargeTestIconCheck;
+       BButton*                        m_pAddMenuButton;
+       BButton*                        m_pDelButton;
+       BButton*                        m_pAddItemButton;
+       BOutlineListView*       m_pMenuOutlineView;
+       BScrollView*            m_pScrollView;  
+};
+
+#endif /* _MenuView_h */

Added: haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuWindow.cpp
===================================================================
--- haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuWindow.cpp          
                (rev 0)
+++ haiku/trunk/src/tests/kits/interface/menu/menuworld/MenuWindow.cpp  
2010-06-12 07:03:01 UTC (rev 37109)
@@ -0,0 +1,358 @@
+//--------------------------------------------------------------------
+//     
+//     MenuWindow.cpp
+//
+//     Written by: Owen Smith
+//     
+//--------------------------------------------------------------------
+
+/*
+       Copyright 1999, Be Incorporated.   All Rights Reserved.
+       This file may be used under the terms of the Be Sample Code License.
+*/
+
+#include <Application.h>
+#include <Box.h>
+#include <CheckBox.h>
+#include <Menu.h>
+#include <MenuBar.h>
+#include <MenuItem.h>
+#include <StringView.h>
+#include <stdio.h>
+#include <string.h>
+
+#include "constants.h"
+#include "MenuView.h"
+#include "MenuWindow.h"
+#include "stddlg.h"
+
+//====================================================================

[... truncated: 2071 lines follow ...]

Other related posts:

  • » [haiku-commits] r37109 - in haiku/trunk/src/tests/kits/interface: . menu menu/menuworld - stefano . ceccherini