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

📄 winmain.cpp

📁 [游戏开发参考书-用DirectX编写RPG游戏]这是一个系列的丛书如果你都看并且懂的话你就可以你工作啦!
💻 CPP
📖 第 1 页 / 共 3 页
字号:
}

BOOL cApp::StartOfCombat()
{
  long i;
  char Filename[MAX_PATH];

  // Clear combat booty
  m_CombatExp = 0;
  m_CombatMoney = 0;
  for(i=0;i<1024;i++)
    m_CombatItems[i] = 0;

  // Trigger start of combat script
  sprintf(Filename, "..\\Data\\SOC%lu.mls", m_SceneNum);
  m_Script.Execute(Filename);

  return TRUE;
}

BOOL cApp::EndOfCombat()
{
  char Filename[MAX_PATH];
  char Text[2000], Gained[128];
  long LevelUp[6] = { 10, 30, 80, 150, 350, 500 }; 
  long i;

  // Give earned combat stuff
  g_PCChar->Def.Money += m_CombatMoney;
  g_PCChar->Def.Experience += m_CombatExp;
  for(i=0;i<1024;i++) {
    if(m_CombatItems[i])
      g_PCChar->CharICS->Add(i, m_CombatItems[i], NULL);
  }

  // Set the header text
  m_Header.SetText("Victory!");

  // Start constructing the main window text
  strcpy(Text, "\r\n\n");

  // Gold gained
  if(m_CombatMoney) {
    sprintf(Gained, "Gained %lu gold!\r\n", m_CombatMoney);
    strcat(Text, Gained);
  }

  // Experience gained
  sprintf(Gained, "Gained %lu experience!\r\n", m_CombatExp);
  strcat(Text, Gained);

  // Process level up 
  for(i=0;i<6;i++) {
    if(g_PCChar->Def.Experience >= LevelUp[i] &&              \
                               g_PCChar->Def.Level < (i+2)) {
      g_PCChar->Def.Level = i+2;
      strcat(Text, "Level up!\r\n");

      // Add bonuses for leveling up
 
      // Abilities
      g_PCChar->Def.HealthPoints += 10;
      g_PCChar->Def.ManaPoints += 10;
      g_PCChar->Def.Attack += 2;
      g_PCChar->Def.Defense += 1;
      g_PCChar->Def.Agility += 1;
      g_PCChar->Def.Resistance += 1;
      g_PCChar->Def.Mental += 1;
      g_PCChar->Def.ToHit += 5;

      strcat(Text, "Stats up!\r\n");

      // Learn spells
      if(i < 5) {
        g_PCChar->Def.MagicSpells[0] |= (1 << i);
        sprintf(Gained, "Learned spell %s\r\n",               \
                         m_SpellController.GetSpell(i)->Name);
        strcat(Text, Gained);
      }

      // Max health and mana to match definition
      g_PCChar->HealthPoints = g_PCChar->Def.HealthPoints;
      g_PCChar->ManaPoints   = g_PCChar->Def.ManaPoints;
    }
  }

  // Add gained items
  for(i=0;i<1024;i++) {
    if(m_CombatItems[i]) {
      sprintf(Gained, "Found %lu x %s\r\n", m_CombatItems[i], \
              m_MIL[i].Name);
      strcat(Text, Gained);
    }
  }

  // Lock the keyboard and mouse
  m_Keyboard.SetLock(KEY_SPACE, TRUE);
  m_Keyboard.SetKeyState(KEY_SPACE, FALSE);
  m_Mouse.SetLock(MOUSE_LBUTTON, TRUE);
  m_Mouse.SetKeyState(MOUSE_LBUTTON, FALSE);

  // Render the scene while waiting for keypress/buttonpress
  while(1) {
    // Break when space pressed
    m_Keyboard.Acquire(TRUE);
    m_Keyboard.Read();
    if(m_Keyboard.GetKeyState(KEY_SPACE) == TRUE)
      break;

    // Break when left mouse button pressed
    m_Mouse.Acquire(TRUE);
    m_Mouse.Read();
    if(m_Mouse.GetButtonState(MOUSE_LBUTTON) == TRUE)
      break;

    // Render the scene w/window
    m_Graphics.ClearZBuffer();
    if(m_Graphics.BeginScene() == TRUE) {
      RenderFrame();
      m_Window.Render(Text);
      m_Header.Render();
      m_Graphics.EndScene();
    }
    m_Graphics.Display();
  }

  // Relock keyboard and mouse
  m_Keyboard.SetLock(KEY_SPACE, TRUE);
  m_Keyboard.SetKeyState(KEY_SPACE, FALSE);
  m_Mouse.SetLock(MOUSE_LBUTTON, TRUE);
  m_Mouse.SetKeyState(MOUSE_LBUTTON, FALSE);

  // Trigger end of combat script
  sprintf(Filename, "..\\Data\\EOC%lu.mls", m_SceneNum);
  m_Script.Execute(Filename);

  return TRUE;
}

int PASCAL WinMain(HINSTANCE hInst, HINSTANCE hPrev,          \
                   LPSTR szCmdLine, int nCmdShow)
{
  cApp App;
  return App.Run();
}

BOOL cApp::SetupTeleport(long Level,                          \
                         float XPos, float YPos, float ZPos)
{
  // Remember which map to teleport to
  m_TeleportMap = Level;

  // Move character to correct teleport location
  m_CharController.Move(0, XPos, YPos, ZPos);

  return TRUE;
}

BOOL cApp::SetupBarter(sCharacter *Character, char *ICSFilename)
{
  g_BarterChar = Character;
  strcpy(g_BarterICS, ICSFilename);
  m_StateManager.Push(BarterFrame, this);

  return TRUE;
}

sCharacter *cApp::GetCharacterAt(long XPos, long YPos)
{
  D3DXVECTOR3 vecRay, vecDir;   
  D3DXVECTOR3 vecMeshRay, vecMeshDir;
  D3DXVECTOR3 vecTemp;          
  D3DXMATRIX  matProj, matView, *matWorld;
  D3DXMATRIX  matInv;           
  DWORD       FaceIndex;
  BOOL        Hit;
  float       u, v, Dist;
  sCharacter  *CharPtr;         
  sMesh      *MeshPtr;

  // Get parent character object  
  if((CharPtr = m_CharController.GetParentCharacter()) == NULL)
    return NULL;

  // Get the project, view, and inversed view matrices
  m_Graphics.GetDeviceCOM()->GetTransform(D3DTS_PROJECTION,   \
                                          &matProj);
  m_Graphics.GetDeviceCOM()->GetTransform(D3DTS_VIEW,         \
                                          &matView);
  D3DXMatrixInverse(&matInv, NULL, &matView);

  // Compute the vector of the pick ray in screen space
  vecTemp.x =  (((2.0f * (float)XPos) /                       \
               (float)m_Graphics.GetWidth()) - 1.0f) /        \
               matProj._11;
  vecTemp.y = -(((2.0f * (float)YPos) /                       \
               (float)m_Graphics.GetHeight()) - 1.0f) /       \
               matProj._22;
  vecTemp.z =  1.0f;

  // Transform the screen space ray
  vecRay.x = matInv._41;
  vecRay.y = matInv._42;
  vecRay.z = matInv._43;
  vecDir.x = vecTemp.x * matInv._11 +                         \
             vecTemp.y * matInv._21 +                         \
             vecTemp.z * matInv._31;
  vecDir.y = vecTemp.x * matInv._12 +                         \
             vecTemp.y * matInv._22 +                         \
             vecTemp.z * matInv._32;
  vecDir.z = vecTemp.x * matInv._13 +                         \
             vecTemp.y * matInv._23 +                         \
             vecTemp.z * matInv._33;

  // Scan through each character and intersect check
  while(CharPtr != NULL) {

    // Scan through character meshes
    MeshPtr = CharPtr->Object.GetMesh()->GetParentMesh();
    while(MeshPtr != NULL) {

      // Transform ray and direction by object's
      // world transformation matrix
      matWorld = CharPtr->Object.GetMatrix();
      D3DXMatrixInverse(&matInv, NULL, matWorld);
      D3DXVec3TransformCoord(&vecMeshRay, &vecRay, &matInv);
      D3DXVec3TransformNormal(&vecMeshDir, &vecDir, &matInv);

      // Check for intersection
      D3DXIntersect(MeshPtr->m_Mesh, &vecMeshRay,&vecMeshDir, \
                    &Hit, &FaceIndex, &u, &v, &Dist);

      // Check if ray hit character and return ID if so
      if(Hit == TRUE)
        return CharPtr;

      // Go to next mesh
      MeshPtr = MeshPtr->m_Next;
    }

    // Go to next character
    CharPtr = CharPtr->Next;
  }

  return NULL;
}

BOOL cApp::LastPointReached(sCharacter *Character)
{
  float XDiff, YDiff, ZDiff;
  float Dist, Radius;

  // Error checking
  if(Character == NULL)
    return FALSE;
  if(Character->AI != CHAR_ROUTE)
    return FALSE;

  // Determine if character has reached point
  XDiff = (float)fabs(Character->XPos -                       \
          Character->Route[Character->NumPoints-1].XPos);
  YDiff = (float)fabs(Character->YPos -                       \
          Character->Route[Character->NumPoints-1].YPos);
  ZDiff = (float)fabs(Character->ZPos -                       \
          Character->Route[Character->NumPoints-1].ZPos);
  Dist = XDiff*XDiff + YDiff*YDiff + ZDiff*ZDiff;
  Radius = m_CharController.GetXZRadius(Character) * 0.25f;
  
  // Return TRUE if point being touched
  if(Dist < (Radius*Radius))
    return TRUE;

  // Last point not being touched
  return FALSE;
}

void cApp::MenuFrame(void *Ptr, long Purpose)
{
  typedef struct {
    float x, y, z;
    float u, v;
  } sMenuVertex;
  sMenuVertex Verts[4] = {
    { -100.0f,  100.0f, 1.0f, 0.0f, 0.0f },
    {  100.0f,  100.0f, 1.0f, 1.0f, 0.0f },
    { -100.0f, -100.0f, 1.0f, 0.0f, 1.0f },
    {  100.0f, -100.0f, 1.0f, 1.0f, 1.0f }
  };
  long MenuFVF = (D3DFVF_XYZ | D3DFVF_TEX1);
  cApp                 *App = (cApp*)Ptr;
  static cVertexBuffer  MenuVB;
  static cTexture       MenuTexture;
  static cTexture       MenuSelect;
  static cCamera        MenuCam;
  static cWorldPosition MenuPos;
  static cFont          MenuFont;
  long                  Num;

  // Initialize menu related data
  if(Purpose == INITPURPOSE) {
    // Create and set the menu vertices
    MenuVB.Create(&App->m_Graphics, 4, MenuFVF,               \
                  sizeof(sMenuVertex));
    MenuVB.Set(0,4,Verts);

    // Load textures
    MenuTexture.Load(&App->m_Graphics, "..\\Data\\MenuBD.bmp");
    MenuSelect.Load(&App->m_Graphics, "..\\Data\\Select.bmp");

    // Create a large font
    MenuFont.Create(&App->m_Graphics, "Times New Roman", 72);

    // Setup the menu camera
    MenuCam.Point(0.0f, 0.0f, -150.0f, 0.0f, 0.0f, 0.0f);

    return;
  }

  // Shutdown resources used in menu
  if(Purpose == SHUTDOWNPURPOSE) {
    MenuVB.Free();
    MenuTexture.Free();
    MenuSelect.Free();
    MenuFont.Free();
    return;
  }

  // Process a frame of menu

  // Exit game or return to game if ESC pressed
  if(App->m_Keyboard.GetKeyState(KEY_ESC) == TRUE) {
    App->m_StateManager.Pop(App);
    return;
  }

  // See which option was selected if mouse button pressed
  if(App->m_Mouse.GetButtonState(MOUSE_LBUTTON) == TRUE) {
    // Lock the mouse button and clear button state
    App->m_Mouse.SetLock(MOUSE_LBUTTON, TRUE);
    App->m_Mouse.SetButtonState(MOUSE_LBUTTON, FALSE);

    // Determine which, if any selection
    Num = App->m_Mouse.GetYPos() - 126;
    if(Num >= 0) {
      Num /= 64;

      // Make sure option enabled 
      if(Num==1 && !(g_MenuOptions & MENU_BACK))
        return;
      if(Num==2 && !(g_MenuOptions & MENU_LOAD))
        return;
      if(Num==3 && !(g_MenuOptions & MENU_SAVE))
        return;

      // Pop the menu state
      App->m_StateManager.Pop(App);

      // Determine what to do based on selection
      switch(Num) {
        case 0: // New game
          // Prepare game data for new game

          // Pop all states
          App->m_StateManager.PopAll(App);

          // Clear all character and spell data
          App->m_CharController.Free();
          App->m_SpellController.Free();

          // Reset script flags
          App->m_Script.Reset();

          // Create the PC and get pointer to him/her
          App->m_CharController.Add(0,0, CHAR_PC, CHAR_STAND, \
                               -100.0f, 0.0f, 50.0f, 3.14f);
          g_PCChar = App->m_CharController.GetCharacter(0);

          // Clear teleport to map #
          App->m_TeleportMap = -1;

          // Push game frame state
          App->m_StateManager.Push(App->GameFrame, App);
  
          // Start new game and let script process as startup
          App->LoadLevel(1);

          break;

        case 1: // Return to game
          App->m_StateManager.Push(App->GameFrame, App);
          break;

        case 2: // Load game
          // Prepare game data for loading game

          // Pop all states
          App->m_StateManager.PopAll(App);

          // Clear all character and spell data
          App->m_CharController.Free();
          App->m_SpellController.Free();

          // Create the PC and get pointer to him/her
          App->m_CharController.Add(0,0, CHAR_PC, CHAR_STAND, \
                               -100.0f, 0.0f, 50.0f, 3.14f);
          g_PCChar = App->m_CharController.GetCharacter(0);

          // Load character's stats and inventory
          App->m_CharController.Load(0, "..\\Data\\Char.cs");
          g_PCChar->CharICS->Load("..\\Data\\Char.ci");

          // Equip weapon
          Num = g_PCChar->Def.Weapon;
          App->m_CharController.Equip(g_PCChar, 0,            \
                                      WEAPON, FALSE);
          if(Num != -1)
            App->m_CharController.Equip(g_PCChar, Num,        \
                                        WEAPON, TRUE);
         
          // Set health and mana to full
          g_PCChar->HealthPoints = g_PCChar->Def.HealthPoints;
          g_PCChar->ManaPoints = g_PCChar->Def.ManaPoints;

          // Load script flags
          App->m_Script.Load("..\\Data\\Script.sav");

          // Clear teleport to map #
          App->m_TeleportMap = -1;

          // Push game frame state
          App->m_StateManager.Push(App->GameFrame, App);

          // Position character
          App->m_CharController.Move(0, 100.0f, 0.0f, -100.0f);

          // Start in town
          App->LoadLevel(1);

          break;

        case 3: // Save game
          // Save script flags
          App->m_Script.Save("..\\Data\\Script.sav");

          // Save character's stats and inventory
          App->m_CharController.Save(0, "..\\Data\\Char.cs");
          g_PCChar->CharICS->Save("..\\Data\\Char.ci");

          break;

        case 4: // Quit game
          App->m_StateManager.PopAll(App);
          break;
      }

      return;
    }
  }

  // Set the menu camera
  App->m_Graphics.SetCamera(&MenuCam);

  // Rotate backdrop vertex buffer world position
  MenuPos.Rotate(0.0f, 0.0f, (float)timeGetTime() / 4000.0f);

  // Render the frame's graphics
  if(App->m_Graphics.BeginScene() == TRUE) {

    // Render backdrop (turning off Z-Buffering first)
    App->m_Graphics.EnableZBuffer(FALSE);
    App->m_Graphics.SetWorldPosition(&MenuPos);
    App->m_Graphics.SetTexture(0, &MenuTexture);
    MenuVB.Render(0, 2, D3DPT_TRIANGLESTRIP);

    // Draw the game's title
    MenuFont.Print("The Tower",0,16,640,0,0xFFFFFFFF,DT_CENTER);

    // Select option based on mouse position
    Num = App->m_Mouse.GetYPos() - 126;
    if(Num >= 0) {
      Num /= 64;

      if(!Num || 
         (Num==1 && (g_MenuOptions & MENU_BACK)) ||
         (Num==2 && (g_MenuOptions & MENU_LOAD)) ||
         (Num==3 && (g_MenuOptions & MENU_SAVE)) ||
         (Num == 4))

⌨️ 快捷键说明

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