トップページ > 過去ログ > 記事閲覧
動作が重くなる原因について
名前:とのがえる 日時: 2009/02/14 18:36

はじめまして、こちらのサイトのライブラリを使用させていただいている者です。 さっそく質問なのですが、下記のコードを実行させるとLoadDivGraphのところでCPUの使用率が50%になってしまい、画像を表示させるところまでいきません。 前に組んだ、他のプログラムでは下記で読み込んでいる画像は表示されたので、画像に問題はないと思われます。 一体原因は何なのでしょうか?? コンパイラはVisualC++ 2005 Express Edtionです。 よろしくお願いします。 /* Gasha2Info.h */ #include "DxLib.h" #include <new> using namespace std; #define SCREEN_W 800 #define SCREEN_H 450 #define SCREEN_P 8 enum MainCharDir { Backward = 3, Right = 6, Forward = 9, Left = 12 }; class BaseCharacter { public: //画像ハンドル int gHandle[12]; //描画するときの座標 int drawPosX; int drawPosY; //中心座標 int centerPosX; int centerPosY; int weight; int direction; //コンストラクタ BaseCharacter(char *media, int width, int hight, int drawX, int drawY, int weight) { //座標類初期化 Initialize(width, hight, drawX, drawY, weight); //画像取得 LoadDivGraph(media, 12, 3, 4, 24, 32, gHandle); } //初期化 void Initialize(int width, int hight, int drawX, int drawY, int weight) { drawPosX = drawX; drawPosY = drawY; centerPosX = drawX + (width / 2); centerPosY = drawY + (hight / 2); this->weight = weight; direction = Forward; } //描画 void Draw() { static unsigned int cnt = 0; // アニメーション用 int ptn; // 描画する ptn = cnt / 10 % 3; DrawGraph(drawPosX, drawPosY, gHandle[ptn + direction], TRUE); } }; /* main.cpp */ #include "Gasha2Info.h" int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow ) { //テクニック用 LONGLONG timeCount; //終了フラグ bool breakFlag = false; //キャラクターの生成 BaseCharacter *b; try { b = new BaseCharacter("media/kokeshi.png", 72, 128, 0, 0, 60); } catch(bad_alloc) { MessageBox(NULL, "死んだ", "いんふぉめーしょん", MB_OK); return -1; } // ウィンドウタイトル SetMainWindowText("ガシャガシャ ver0.2"); //ウィンドウサイズ if(SetGraphMode(SCREEN_W, SCREEN_H, SCREEN_P) != DX_CHANGESCREEN_OK) exit(-1); //ウィンドウモード ChangeWindowMode(TRUE); if(DxLib_Init()==-1) return -1; SetDrawScreen(DX_SCREEN_BACK); //ゲーム本体(終了フラグが立つまでループ) do { // テクニック:同期用 timeCount = GetNowHiPerformanceCount(); // 画面に描かれているものをすべて消す ClearDrawScreen(); // 点を打つ //DrawPixel(400, 225, 0xffff); //キャラクターの描画 b->Draw(); // 裏画面の内容を表画面に反映させる ScreenFlip(); if(ProcessMessage()==-1) exit(-1); if(CheckHitKey(KEY_INPUT_ESCAPE)) { int exitCheck = MessageBox(NULL, "続ける??", "いんふぉめーしょん", MB_YESNO); if(exitCheck == IDNO) breakFlag = 1; } // テクニック:どのマシンでも60Hzで動作させる while(GetNowHiPerformanceCount() - timeCount < 16667) if(ProcessMessage() == -1) break; }while(!breakFlag); //キャラクター解放 delete b; // DXライブラリ使用の終了処理 DxLib_End(); // ソフトの終了 return 0 ; }

Page: 1 |

Re: 動作が重くなる原因について ( No.1 )
名前:管理人 日時:2009/02/15 12:18

DxLib_Init の前に LoadDivGraph を呼んでも正常に動作しませんので、 new BaseCharacter を実行するより前に DxLib_Init を呼ぶようにしてみてください
Re: 動作が重くなる原因について ( No.2 )
名前:とのがえる 日時:2009/02/15 14:12

new BaseCharacterをDxLib_Initの後に置いたら描画できました、本当にありがとうございます。(初歩的なものですみません…) ですが、やはりCPUの使用率が30%ほどになってしまいます、これにはどういったものが考えられるのでしょうか??
Re: 動作が重くなる原因について ( No.3 )
名前:管理人 日時:2009/02/16 20:00

処理が軽くても CPU 使用率が高くなる原因は ScreenFlip にあります まず、CPU 使用率は Sleep や WaitMessage 等のスレッドの処理を一時的に停止する WindowsAPI を 使用しない限りはどんなにゲームの処理が軽くても 100% になります、 そして、ScreenFlip はデフォルトの設定ではティアリング回避のために垂直同期期間に入ってから 裏画面と表画面を切り替えるのですが、DXライブラリでは前回の ScreenFlip から 10ミリ秒以下しか 時間が経過していない場合のみ Sleep で処理を一時停止するようにしています なので、仮にモニタのリフレッシュレートが 60Hz だった場合、ある垂直同期期間から次の 垂直同期期間に入るまでの時間は、大体 1000ms ÷ 60Hz ≒ 16.66ms ( ms = ミリ秒 ) 約14ミリ秒なのですが( 垂直同期期間自体は短く、1〜2ミリ秒です )、この14ミリ秒の内 10ミリ秒以降は垂直同期期間に入ったかどうかをループでぐるぐるとチェックし続けているので その間 CPU は休んでいることにならず、仮に一つ前の ScreenFlip から殆ど処理もせずに 再び ScreenFlip を呼んでも CPU 使用率が数十パーセントになるというわけです 10ミリ秒経過しても同期期間に入るまではまだ約4ミリ秒あるので、更に Sleep しても 良いのですが、環境によっては 10ミリ秒以上 Sleep すると同期期間を取りこぼしたり することがあるので、CPU使用率よりソフトの安定動作を優先して Sleep するのは 10ミリ秒 ということにしてあります と、これだけ長々と解説しておいて手元にある DirectX9 版のDXライブラリで調べてみたら ScreenFlip だけ呼ぶループのプログラムでは CPU 使用率が5%だったり・・・( DirectX7 版では 同様のプログラムで CPU使用率 40% ) DirectX7 を使っている弊害かもしれません・・・
Re: 動作が重くなる原因について ( No.4 )
名前:とのがえる 日時:2009/02/17 17:42

丁寧に説明してくださってありがとうございます!! お話を聞く限りでは、自分ではどうしようもなさそうなので、組んだプログラムのせいじゃない!とポジティブに考えておこうと思います(笑) 本当にありがとうございました

Page: 1 |