⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 guimenubar.cc

📁 五行MMORPG引擎系统V1.0
💻 CC
📖 第 1 页 / 共 2 页
字号:
         curX += walk->bounds.extent.x;
      }
		mouseOverMenu = NULL;
		mouseDownMenu = NULL;
   }
}

void GuiMenuBar::checkMenuMouseMove(const GuiEvent &event)
{
   Menu *hit = findHitMenu(event.mousePoint);
   if(hit && hit != mouseDownMenu)
   {
      // gotta close out the current menu...
      mTextList->setSelectedCell(Point2I(-1, -1));
      closeMenu();
      mouseOverMenu = mouseDownMenu = hit;
      setUpdate();
      onAction();
   }
}

void GuiMenuBar::onMouseMove(const GuiEvent &event)
{
   Menu *hit = findHitMenu(event.mousePoint);
	if(hit != mouseOverMenu)
	{
		mouseOverMenu = hit;
		setUpdate();
	}
}

void GuiMenuBar::onMouseLeave(const GuiEvent &event)
{
   if(mouseOverMenu)
		setUpdate();
	mouseOverMenu = NULL;
}

void GuiMenuBar::onMouseDragged(const GuiEvent &event)
{
   Menu *hit = findHitMenu(event.mousePoint);
	
	if(hit != mouseOverMenu)
	{
		mouseOverMenu = hit;
      mouseDownMenu = hit;
		setUpdate();
      onAction();
	}
}

void GuiMenuBar::onMouseDown(const GuiEvent &event)
{
   mouseDownMenu = mouseOverMenu = findHitMenu(event.mousePoint);
	setUpdate();
   onAction();
}

void GuiMenuBar::onMouseUp(const GuiEvent &event)
{
   mouseDownMenu = NULL;
	setUpdate();
}

void GuiMenuBar::onRender(Point2I offset, const RectI &updateRect)
{
   //if opaque, fill the update rect with the fill color
   if (mProfile->mOpaque)
      dglDrawRectFill(RectI(offset, mBounds.extent), mProfile->mFillColor);

   for(Menu *walk = menuList; walk; walk = walk->nextMenu)
   {
      if(!walk->visible)
         continue;
      ColorI fontColor = mProfile->mFontColor;
      RectI bounds = walk->bounds;
      bounds.point += offset;

      Point2I start;

      start.x = walk->bounds.point.x + 6;
      start.y = walk->bounds.point.y + ( walk->bounds.extent.y - ( mProfile->mFont->getHeight() - 2 ) ) / 2;


#ifdef TGE_RPG_UI ///TGE_RPG_UI
      if(walk == mouseDownMenu)
         renderFilledBorder(bounds, mProfile->mBorderColorHL,mProfile->mFillColorHL);
      else if(walk == mouseOverMenu && mouseDownMenu == NULL)
         renderFilledBorder(bounds, mProfile->mBorderColor,mProfile->mFillColorHL);
#else
      if(walk == mouseDownMenu)
         renderSlightlyLoweredBox(bounds, mProfile);
      else if(walk == mouseOverMenu && mouseDownMenu == NULL)
         renderSlightlyRaisedBox(bounds, mProfile);
#endif

      dglSetBitmapModulation( fontColor );

      dglDrawText( mProfile->mFont, start + offset, walk->text, mProfile->mFontColors );
   }
}

void GuiMenuBar::buildAcceleratorMap()
{
   Parent::buildAcceleratorMap();
   // ok, accelerator map is cleared...
   // add all our keys:
   mCurAcceleratorIndex = 1;

   for(Menu *menu = menuList; menu; menu = menu->nextMenu)
   {
      for(MenuItem *item = menu->firstMenuItem; item; item = item->nextMenuItem)
      {
         if(!item->accelerator)
         {
            item->accelerator = 0;
            continue;
         }
         EventDescriptor accelEvent;
			ActionMap::createEventDescriptor(item->accelerator, &accelEvent);

         //now we have a modifier, and a key, add them to the canvas
         GuiCanvas *root = getRoot();
         if (root)
            root->addAcceleratorKey(this, mCurAcceleratorIndex, accelEvent.eventCode, accelEvent.flags);
         item->acceleratorIndex = mCurAcceleratorIndex;
         mCurAcceleratorIndex++;
      }
   }
}

void GuiMenuBar::acceleratorKeyPress(U32 index)
{
   // loop through all the menus
   // and find the item that corresponds to the accelerator index
   for(Menu *menu = menuList; menu; menu = menu->nextMenu)
   {
      if(!menu->visible)
         continue;

      for(MenuItem *item = menu->firstMenuItem; item; item = item->nextMenuItem)
      {
         if(item->acceleratorIndex == index)
         {
            // first, call the script callback for menu selection:
            Con::executef( this, 4, "onMenuSelect", Con::getIntArg(menu->id),
                        menu->text);
            if(item->visible)
               menuItemSelected(menu, item);
            return;
         }
      }
   }
}

//------------------------------------------------------------------------------
// Menu display class methods
//------------------------------------------------------------------------------

GuiMenuBackgroundCtrl::GuiMenuBackgroundCtrl(GuiMenuBar *ctrl, GuiMenuTextListCtrl *textList)
{
   mMenuBarCtrl = ctrl;
   mTextList = textList;
}

void GuiMenuBackgroundCtrl::onMouseDown(const GuiEvent &event)
{
   mTextList->setSelectedCell(Point2I(-1,-1));
   mMenuBarCtrl->closeMenu();
}

void GuiMenuBackgroundCtrl::onMouseMove(const GuiEvent &event)
{
   GuiCanvas *root = getRoot();
   GuiControl *ctrlHit = root->findHitControl(event.mousePoint, mLayer - 1);
   if(ctrlHit == mMenuBarCtrl)  // see if the current mouse over menu is right...
      mMenuBarCtrl->checkMenuMouseMove(event);
}

void GuiMenuBackgroundCtrl::onMouseDragged(const GuiEvent &event)
{
   GuiCanvas *root = getRoot();
   GuiControl *ctrlHit = root->findHitControl(event.mousePoint, mLayer - 1);
   if(ctrlHit == mMenuBarCtrl)  // see if the current mouse over menu is right...
      mMenuBarCtrl->checkMenuMouseMove(event);
}

GuiMenuTextListCtrl::GuiMenuTextListCtrl(GuiMenuBar *ctrl)
{
   mMenuBarCtrl = ctrl;
}

void GuiMenuTextListCtrl::onRenderCell(Point2I offset, Point2I cell, bool selected, bool mouseOver)
{
   if(dStrcmp(mList[cell.y].text + 2, "-\t"))
      Parent::onRenderCell(offset, cell, selected, mouseOver);
   else
   {
      S32 yp = offset.y + mCellSize.y / 2;
      dglDrawLine(offset.x, yp, offset.x + mCellSize.x, yp, ColorI(128,128,128));
      dglDrawLine(offset.x, yp+1, offset.x + mCellSize.x, yp+1, ColorI(255,255,255));
   }
   // now see if there's a bitmap...
   U8 idx = mList[cell.y].text[0];
   if(idx != 1)
   {
      // there's a bitmap...
      U32 index = U32(idx - 2) * 3;
      if(!mList[cell.y].active)
         index += 2;
      else if(selected || mouseOver)
         index ++;

      RectI rect = mProfile->mBitmapArrayRects[index];

#ifdef TGE_RPG_UI ///TGE_RPG_UI
      Point2I off;
		off.y = (mCellSize.y - rect.extent.y)/2;
		off.x = 2;
		if(selected || mouseOver)
			off.y--;
#else
      Point2I off = mMenuBarCtrl->maxBitmapSize - rect.extent;
      off /= 2;
#endif

      dglClearBitmapModulation();
      dglDrawBitmapSR(mProfile->mTextureHandle, offset + off, rect);
   }
}

bool GuiMenuTextListCtrl::onKeyDown(const GuiEvent &event)
{
   //if the control is a dead end, don't process the input:
   if ( !mVisible || !mActive || !mAwake )
      return false;

   //see if the key down is a <return> or not
   if ( event.modifier == 0 )
   {
      if ( event.keyCode == KEY_RETURN )
      {
         mMenuBarCtrl->closeMenu();
         return true;
      }
      else if ( event.keyCode == KEY_ESCAPE )
      {
         mSelectedCell.set( -1, -1 );
         mMenuBarCtrl->closeMenu();
         return true;
      }
   }

   //otherwise, pass the event to it's parent
   return Parent::onKeyDown(event);
}

void GuiMenuTextListCtrl::onMouseDown(const GuiEvent &event)
{
   Parent::onMouseDown(event);
   mMenuBarCtrl->closeMenu();
}

void GuiMenuTextListCtrl::onMouseUp(const GuiEvent &event)
{
   // ok, this is kind of strange... but!
   // here's the deal: if we get a mouse up in this control
   // it means the mouse was dragged from the initial menu mouse click
   // so: activate the menu result as though this event were,
   // instead, a mouse down.

   onMouseDown(event);
}

//------------------------------------------------------------------------------

void GuiMenuBar::menuItemSelected(GuiMenuBar::Menu *menu, GuiMenuBar::MenuItem *item)
{
   if(item->enabled)
      Con::executef( this, 6, "onMenuItemSelect", Con::getIntArg(menu->id),
               menu->text, Con::getIntArg(item->id), item->text);
}

void GuiMenuBar::onSleep()
{
   if(mBackground) // a menu is up?
   {
      mTextList->setSelectedCell(Point2I(-1, -1));
      closeMenu();
   }
   Parent::onSleep();
}

void GuiMenuBar::closeMenu()
{
   // Get the selection from the text list:
   S32 selectionIndex = mTextList->getSelectedCell().y;

   // Pop the background:
   getRoot()->popDialogControl(mBackground);

   // Kill the popup:
   mBackground->deleteObject();
   mBackground = NULL;

   // Now perform the popup action:
   if ( selectionIndex != -1 )
   {
      MenuItem *list = mouseDownMenu->firstMenuItem;

      while(selectionIndex && list)
      {
         list = list->nextMenuItem;
         selectionIndex--;
      }
      if(list)
         menuItemSelected(mouseDownMenu, list);
   }
   mouseDownMenu = NULL;
}

//------------------------------------------------------------------------------
void GuiMenuBar::onAction()
{
   if(!mouseDownMenu)
      return;

   // first, call the script callback for menu selection:
   Con::executef( this, 4, "onMenuSelect", Con::getIntArg(mouseDownMenu->id),
               mouseDownMenu->text);

   MenuItem *visWalk = mouseDownMenu->firstMenuItem;
   while(visWalk)
   {
      if(visWalk->visible)
         break;
      visWalk = visWalk->nextMenuItem;
   }
   if(!visWalk)
   {
      mouseDownMenu = NULL;
      return;
   }

   mTextList = new GuiMenuTextListCtrl(this);
   mTextList->mProfile = mProfile;

   mBackground = new GuiMenuBackgroundCtrl(this, mTextList);

   GuiCanvas *root = getRoot();
   Point2I windowExt = root->mBounds.extent;

   mBackground->mBounds.point.set(0,0);
   mBackground->mBounds.extent = root->mBounds.extent;

   S32 textWidth = 0, width = 0;
   S32 acceleratorWidth = 0;

   GFont *font = mProfile->mFont;

   for(MenuItem *walk = mouseDownMenu->firstMenuItem; walk; walk = walk->nextMenuItem)
   {
      if(!walk->visible)
         continue;

      S32 iTextWidth = font->getStrWidth((const UTF8 *)walk->text);
      S32 iAcceleratorWidth = walk->accelerator ? font->getStrWidth((const UTF8 *)walk->accelerator) : 0;

      if(iTextWidth > textWidth)
         textWidth = iTextWidth;
      if(iAcceleratorWidth > acceleratorWidth)
         acceleratorWidth = iAcceleratorWidth;
   }
   width = textWidth + acceleratorWidth + maxBitmapSize.x * 2 + 2 + 4;

#ifdef TGE_RPG ///TGE_RPG
   mTextList->setCellSize(Point2I(width, font->getHeight()+6));
#else
   mTextList->setCellSize(Point2I(width, font->getHeight()+3));
#endif
   mTextList->clearColumnOffsets();
   mTextList->addColumnOffset(-1); // add an empty column in for the bitmap index.
   mTextList->addColumnOffset(maxBitmapSize.x + 1);
   mTextList->addColumnOffset(maxBitmapSize.x + 1 + textWidth + 4);

   U32 entryCount = 0;

#ifdef TGE_RPG_UI ///TGE_RPG_UI
	char szAcc[64];
#endif
   for(MenuItem *walk = mouseDownMenu->firstMenuItem; walk; walk = walk->nextMenuItem)
   {
      if(!walk->visible)
         continue;

      char buf[512];
      char bitmapIndex = 1;
      if(walk->bitmapIndex >= 0 && (walk->bitmapIndex * 3 <= mProfile->mBitmapArrayRects.size()))
         bitmapIndex = walk->bitmapIndex + 2;
#ifdef TGE_RPG_UI ///TGE_RPG_UI
		if(walk->accelerator)
		{	
			dStrcpy(szAcc,walk->accelerator);
			char* pSpace = dStrstr((const char*)szAcc," ");
			if(pSpace)
				pSpace[0] = '+';
		}
		else
			szAcc[0] = 0;
      dSprintf(buf, sizeof(buf), "%c\t%s\t%s", bitmapIndex, walk->text, szAcc);
#else
      dSprintf(buf, sizeof(buf), "%c\t%s\t%s", bitmapIndex, walk->text, walk->accelerator ? walk->accelerator : "");
#endif

      mTextList->addEntry(entryCount, buf);

      if(!walk->enabled)
         mTextList->setEntryActive(entryCount, false);

      entryCount++;
   }
   Point2I menuPoint = localToGlobalCoord(mouseDownMenu->bounds.point);
   menuPoint.y += mouseDownMenu->bounds.extent.y + 2;

   GuiControl *ctrl = new GuiControl;
   ctrl->mBounds.point = menuPoint;
   ctrl->mBounds.extent = mTextList->mBounds.extent + Point2I(6, 6);
   ctrl->mProfile = mProfile;
   mTextList->mBounds.point += Point2I(3,3);

   //mTextList->mBounds.point = Point2I(3,3);

   mTextList->registerObject();
   mBackground->registerObject();
   ctrl->registerObject();

   mBackground->addObject( ctrl );
   ctrl->addObject( mTextList );

   root->pushDialogControl(mBackground, mLayer + 1);
   mTextList->setFirstResponder();
}


⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -