LoginSignup
11
3

More than 5 years have passed since last update.

[openframeworks] ウィンドウサイズはキャッシュしましょう, というお話

Last updated at Posted at 2017-05-18

結論

(Macでは?)ウィンドウサイズはキャッシュしましょう

上級者の方は何を当たり前のことをって言うと思うのでここで終了です.

よく分からない人向け

久しぶりにそこそこ複雑な描画をするアプリをoFで書いていたのですが, フルスクリーンにしたらフレームレート劇落ち君問題に遭遇しまして, どこがボトルネックか突き止めるのにだいぶ時間が掛かったんですけど, 取り敢えずバカっぽく

class ofApp : public ofBaseApp {
    void setup() {
        ...
    }
    void update() {
        ...
    }
    void draw() {
        float t = ofGetElapsedTimef();
        ...
        ofLogNotice() << (ofGetElapsedTimef() - t);
    }
};

って書くじゃないですか. 書いたんですよ.
で, フルスクリーン時とフルスクリーンじゃないときでほぼ差が無いわけですよ.
そもそも最初にFullHDで設定しててMBPでフルスクリーンにしても1920x1200じゃないですか.
9:10くらいだからバカみたいに考えると10%くらいしか処理負荷上がらないはずじゃないですか.
でもフレームレートは60fpsだったのが15fpsくらいまで落ちるわけです.

で, このアプリ, 立ち上がりから数十秒掛けて徐々に要素が増えていくんですけどフルスクリーンでも最初は60fpsなんだけど要素で揃うと15fpsになるんですね. フルスクリーンだと.
フルスクリーンじゃないときは100年経っても60fpsなんですよ.

そうなるとバカでも気付くじゃないですか. その要素の中身が悪いって.
だから

class ofApp : public ofBaseApp {
    void setup() {
        ...
    }
    void update() {
        float t = ofGetElapsedTimef();
        ...
        ofLogNotice("update") << (ofGetElapsedTimef() - t);
    }
    void draw() {
        float t = ofGetElapsedTimef();
        ...
        ofLogNotice("draw") << (ofGetElapsedTimef() - t);
    }
};

こうしますよね.

そしたら案の定updateが重くなるんです. それも異常な感じで跳ね上がるんです.
でもここでやってるのは簡単な範囲判定的なことなんですよね.

なんか状況説明書いてくのもめんどくさくなったんでそろそろ結論にしますけど

class ofApp : public ofBaseApp {
    bool calc{false};
public:
    void update() {
        if(calc) {
            float t = ofGetElapsedTimef();
            for(std::size_t i = 0; i < 10000; i++) float f = ofGetWidth();
            ofLogNotice() << (ofGetElapsedTimef() - t);
            calc = false;
        }
    }

    void keyPressed(int key) {
        if(key == ' ') calc = true;
        if(key == 'f') ofToggleFullscreen();
    }
};

これで非フルスクリーン時とフルスクリーン時で計測してみると

[notice ] 0.000224233
[notice ] 5.37182

(Touchbar MBP+MacOS Sierra, oF0.9.8 で計測)

はい. 10000倍くらい違います. このループ回数を100000にしたらクラッシュします.

なので超大雑把ですけど

ofRectangle windowRect;

void setup() {
    windowRect.set(ofGetWidth(), ofGetHeight());
}

void windowResized() {
    windowRect.set(ofGetWidth(), ofGetHeight());
}

こうやってwindowRect使いましょ. ってお話でした.

追記

ランボー 怒りのaddon化
https://github.com/2bbb/ofxCachedSize

11
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
11
3