PuzzleSDK
NewRendererTest.cpp
浏览该文件的文档.
1/****************************************************************************
2 Copyright (c) 2013 cocos2d-x.org
3 Copyright (c) 2017-2018 Xiamen Yaji Software Co., Ltd.
4
5 http://www.cocos2d-x.org
6
7 Permission is hereby granted, free of charge, to any person obtaining a copy
8 of this software and associated documentation files (the "Software"), to deal
9 in the Software without restriction, including without limitation the rights
10 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11 copies of the Software, and to permit persons to whom the Software is
12 furnished to do so, subject to the following conditions:
13
14 The above copyright notice and this permission notice shall be included in
15 all copies or substantial portions of the Software.
16
17 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
23 THE SOFTWARE.
24 ****************************************************************************/
25
26#include "NewRendererTest.h"
27#include <chrono>
28#include <sstream>
29#include "renderer/backend/Device.h"
30
32
34public:
35 void startTick(const std::string &key) {
36 _durations[key] = - now();
37 }
38
39 int endTick(const std::string &key) {
40 auto n = now();
41 auto itr = _durations.find(key);
42 if(_durations.find(key) == _durations.end())
43 {
44 return -1;
45 }
46 else if(itr->second < 0) {
47 itr->second = n + itr->second;
48 }
49 return static_cast<int>(itr->second);
50 }
51
52 inline int64_t now() const{
53 return std::chrono::duration_cast<std::chrono::nanoseconds>(std::chrono::steady_clock::now().time_since_epoch()).count();
54 }
55
56 void reset() {
57 _durations.clear();
58 }
59
60private:
61 std::map<std::string, int64_t > _durations;
62};
63
64
65
66NewRendererTests::NewRendererTests()
67{
68
71// ADD_TEST_CASE(NewClippingNodeTest); // When depth and stencil are used together, ...
83};
84
85std::string MultiSceneTest::title() const
86{
87 return "New Renderer";
88}
89
90std::string MultiSceneTest::subtitle() const
91{
92 return "MultiSceneTest";
93}
94
96{
97 auto touchListener = EventListenerTouchAllAtOnce::create();
98 touchListener->onTouchesEnded = CC_CALLBACK_2(NewSpriteTest::onTouchesEnded, this);
99
102}
103
105{
106
107}
108
110{
111 Size winSize = Director::getInstance()->getWinSize();
112
113 Sprite* parent = Sprite::create("Images/grossini.png");
114 parent->setPosition(winSize.width/4, winSize.height/2);
115 Sprite* child1 = Sprite::create("Images/grossinis_sister1.png");
116 child1->setPosition(0.0f, -20.0f);
117 Sprite* child2 = Sprite::create("Images/grossinis_sister2.png");
118 child2->setPosition(20.0f, -20.0f);
119 Sprite* child3 = Sprite::create("Images/grossinis_sister1.png");
120 child3->setPosition(40.0f, -20.0f);
121 Sprite* child4 = Sprite::create("Images/grossinis_sister2.png");
122 child4->setPosition(60.0f, -20.0f);
123 Sprite* child5 = Sprite::create("Images/grossinis_sister2.png");
124 child5->setPosition(80.0f, -20.0f);
125 Sprite* child6 = Sprite::create("Images/grossinis_sister2.png");
126 child6->setPosition(100.0f, -20.0f);
127 Sprite* child7 = Sprite::create("Images/grossinis_sister2.png");
128 child7->setPosition(120.0f, -20.0f);
129
130 parent->addChild(child1);
131 parent->addChild(child2);
132 parent->addChild(child3);
133 parent->addChild(child4);
134 parent->addChild(child5);
135 parent->addChild(child6);
136 parent->addChild(child7);
137 addChild(parent);
138}
139
141{
142 Size winSize = Director::getInstance()->getWinSize();
143
144 Sprite* parent = Sprite::create("Images/grossini.png");
145 parent->setPosition(winSize.width*2/3, winSize.height/2);
146 Sprite* child1 = Sprite::create("Images/grossinis_sister1.png");
147 child1->setPosition(0.0f, -20.0f);
148 Sprite* child2 = Sprite::create("Images/grossinis_sister2.png");
149 child2->setPosition(20.0f, -20.0f);
150 Sprite* child3 = Sprite::create("Images/grossinis_sister1.png");
151 child3->setPosition(40.0f, -20.0f);
152 Sprite* child4 = Sprite::create("Images/grossinis_sister2.png");
153 child4->setPosition(60.0f, -20.0f);
154 Sprite* child5 = Sprite::create("Images/grossinis_sister2.png");
155 child5->setPosition(80.0f, -20.0f);
156 Sprite* child6 = Sprite::create("Images/grossinis_sister2.png");
157 child6->setPosition(100.0f, -20.0f);
158 Sprite* child7 = Sprite::create("Images/grossinis_sister2.png");
159 child7->setPosition(120.0f, -20.0f);
160
161 parent->addChild(child1);
162 parent->addChild(child2);
163 parent->addChild(child3);
164 parent->addChild(child4);
165 parent->addChild(child5);
166 parent->addChild(child6);
167 parent->addChild(child7);
168 addChild(parent);
169}
170
171void NewSpriteTest::onTouchesEnded(const std::vector<Touch *> &touches, Event *event)
172{
173
174}
175
176std::string NewSpriteTest::title() const
177{
178 return "Renderer";
179}
180
181std::string NewSpriteTest::subtitle() const
182{
183 return "SpriteTest";
184}
185
186class SpriteInGroupCommand : public Sprite
187{
188protected:
190public:
191 static SpriteInGroupCommand* create(const std::string& filename);
192
193 virtual void draw(Renderer *renderer, const Mat4 &transform, uint32_t flags) override;
194};
195
197{
198 SpriteInGroupCommand* sprite = new (std::nothrow) SpriteInGroupCommand();
199 sprite->initWithFile(filename);
200 sprite->autorelease();
201 return sprite;
202}
203
204void SpriteInGroupCommand::draw(Renderer *renderer, const Mat4 &transform, uint32_t flags)
205{
206 CCASSERT(renderer, "Render is null");
207 _spriteWrapperCommand.init(_globalZOrder);
208 renderer->addCommand(&_spriteWrapperCommand);
209 renderer->pushGroup(_spriteWrapperCommand.getRenderQueueID());
210 Sprite::draw(renderer, transform, flags);
211 renderer->popGroup();
212}
213
215{
216 auto sprite = SpriteInGroupCommand::create("Images/grossini.png");
217 Size winSize = Director::getInstance()->getWinSize();
218 sprite->setPosition(winSize.width/2,winSize.height/2);
219 addChild(sprite);
220}
221
223{
224}
225
226std::string GroupCommandTest::title() const
227{
228 return "Renderer";
229}
230
231std::string GroupCommandTest::subtitle() const
232{
233 return "GroupCommandTest: You should see a sprite";
234}
235
237{
238 auto s = Director::getInstance()->getWinSize();
239
240 auto clipper = ClippingNode::create();
241 clipper->setTag( kTagClipperNode );
242 clipper->setContentSize( Size(200.0f, 200.0f) );
243 clipper->setAnchorPoint( Vec2(0.5f, 0.5f) );
244 clipper->setPosition( Vec2(s.width / 2, s.height / 2) );
245
246 clipper->runAction(RepeatForever::create(RotateBy::create(1, 45)));
247 this->addChild(clipper);
248
249 // TODO: Fix draw node as clip node
250// auto stencil = NewDrawNode::create();
251// Vec2 rectangle[4];
252// rectangle[0] = Vec2(0, 0);
253// rectangle[1] = Vec2(clipper->getContentSize().width, 0);
254// rectangle[2] = Vec2(clipper->getContentSize().width, clipper->getContentSize().height);
255// rectangle[3] = Vec2(0, clipper->getContentSize().height);
256//
257// Color4F white(1, 1, 1, 1);
258// stencil->drawPolygon(rectangle, 4, white, 1, white);
259// clipper->setStencil(stencil);
260
261 //Test with alpha Test
262 clipper->setAlphaThreshold(0.05f);
263 auto stencil = Sprite::create("Images/grossini.png");
264 stencil->setPosition(s.width/2, s.height/2);
265 clipper->setStencil(stencil);
266
267 auto content = Sprite::create("Images/background2.png");
268 content->setTag( kTagContentNode );
269 content->setAnchorPoint( Vec2(0.5f, 0.5f) );
270 content->setPosition( Vec2(clipper->getContentSize().width / 2, clipper->getContentSize().height / 2) );
271 clipper->addChild(content);
272
273 _scrolling = false;
274
275 auto listener = EventListenerTouchAllAtOnce::create();
276 listener->onTouchesBegan = CC_CALLBACK_2(NewClippingNodeTest::onTouchesBegan, this);
277 listener->onTouchesMoved = CC_CALLBACK_2(NewClippingNodeTest::onTouchesMoved, this);
278 listener->onTouchesEnded = CC_CALLBACK_2(NewClippingNodeTest::onTouchesEnded, this);
279 _eventDispatcher->addEventListenerWithSceneGraphPriority(listener, this);
280}
281
283{
284
285}
286
287std::string NewClippingNodeTest::title() const
288{
289 return "New Render";
290}
291
293{
294 return "ClipNode";
295}
296
297void NewClippingNodeTest::onTouchesBegan(const std::vector<Touch *> &touches, Event *event)
298{
299 Touch *touch = touches[0];
300 auto clipper = this->getChildByTag(kTagClipperNode);
301 Vec2 point = clipper->convertToNodeSpace(Director::getInstance()->convertToGL(touch->getLocationInView()));
302 auto rect = Rect(0, 0, clipper->getContentSize().width, clipper->getContentSize().height);
303 _scrolling = rect.containsPoint(point);
304 _lastPoint = point;
305}
306
307void NewClippingNodeTest::onTouchesMoved(const std::vector<Touch *> &touches, Event *event)
308{
309 if (!_scrolling) return;
310 Touch *touch = touches[0];
311 auto clipper = this->getChildByTag(kTagClipperNode);
312 auto point = clipper->convertToNodeSpace(Director::getInstance()->convertToGL(touch->getLocationInView()));
313 Vec2 diff = point - _lastPoint;
314 auto content = clipper->getChildByTag(kTagContentNode);
315 content->setPosition(content->getPosition() + diff);
316 _lastPoint = point;
317}
318
319void NewClippingNodeTest::onTouchesEnded(const std::vector<Touch *> &touches, Event *event)
320{
321 if (!_scrolling) return;
322 _scrolling = false;
323}
324
329{
330 auto s = Director::getInstance()->getWinSize();
331
332 auto parent = Node::create();
333 parent->setPosition(s.width/2, s.height/2);
334 addChild(parent);
335
336 auto rectNode = DrawNode::create();
337 Vec2 rectangle[4];
338 rectangle[0] = Vec2(-50, -50);
339 rectangle[1] = Vec2(50, -50);
340 rectangle[2] = Vec2(50, 50);
341 rectangle[3] = Vec2(-50, 50);
342
343 Color4F white(1, 1, 1, 1);
344 rectNode->drawPolygon(rectangle, 4, white, 1, white);
345 parent->addChild(rectNode);
346}
347
349{
350
351}
352
353std::string NewDrawNodeTest::title() const
354{
355 return "New Render";
356}
357
358std::string NewDrawNodeTest::subtitle() const
359{
360 return "DrawNode";
361}
362
364{
365 Size size = Director::getInstance()->getWinSize();
366 auto sprite = Sprite::create("Images/btn-about-normal-vertical.png");
367 sprite->setRotation(5);
368 sprite->setPosition(Vec2(size.width/2,size.height/3));
369 sprite->setScale(2);
370 addChild(sprite);
371
372 auto sprite2 = Sprite::create("Images/btn-about-normal-vertical.png");
373 sprite2->setRotation(-85);
374 sprite2->setPosition(Vec2(size.width/2,size.height * 2/3));
375 sprite2->setScale(2);
376 addChild(sprite2);
377
378 auto listener = EventListenerTouchOneByOne::create();
379 listener->setSwallowTouches(true);
380
381 listener->onTouchBegan = CC_CALLBACK_2(NewCullingTest::onTouchBegan, this);
382 listener->onTouchMoved = CC_CALLBACK_2(NewCullingTest::onTouchMoved, this);
383
384 _eventDispatcher->addEventListenerWithSceneGraphPriority(listener, this);
385
386}
387
388bool NewCullingTest::onTouchBegan(Touch* touch, Event *event)
389{
390 auto pos = touch->getLocation();
391 _lastPos = pos;
392 return true;
393}
394
395void NewCullingTest::onTouchMoved(Touch* touch, Event *event)
396{
397 auto pos = touch->getLocation();
398
399 auto offset = pos - _lastPos;
400
401 auto layerPos = getPosition();
402 auto newPos = layerPos + offset;
403
404 setPosition(newPos);
405 _lastPos = pos;
406}
407
409{
410
411}
412
413std::string NewCullingTest::title() const
414{
415 return "New Render";
416}
417
418std::string NewCullingTest::subtitle() const
419{
420 return "Drag the layer to test the result of culling";
421}
422
424{
425
426 Size s = Director::getInstance()->getWinSize();
427 Node* parent = Node::create();
428 parent->setPosition(s.width / 2,s.height / 2);
429 addChild(parent);
430
431
432#define KEY_CREATION "11"
433#define KEY_DESTROYATION "22"
434
435 labelCreate = Label::createWithTTF(TTFConfig("fonts/arial.ttf"), "Sprite Creation: ..");
436 labelDestory= Label::createWithTTF(TTFConfig("fonts/arial.ttf"), "Destroy Sprites: ..");
437
438 MenuItemFont::setFontName("fonts/arial.ttf");
439 MenuItemFont::setFontSize(65);
440 auto decrease = MenuItemFont::create(" - ", CC_CALLBACK_1(SpriteCreation::delSpritesCallback, this));
441 decrease->setColor(Color3B(0, 200, 20));
442 auto increase = MenuItemFont::create(" + ", CC_CALLBACK_1(SpriteCreation::addSpritesCallback, this));
443 increase->setColor(Color3B(0, 200, 20));
444
445 auto menu = Menu::create(decrease, increase, nullptr);
446 menu->alignItemsHorizontally();
447 menu->setPosition(Vec2(s.width / 2, s.height - 105));
448 addChild(menu, 1);
449
450 TTFConfig ttfCount("fonts/Marker Felt.ttf", 30);
451 _labelSpriteNum = Label::createWithTTF(ttfCount, "Label");
452 _labelSpriteNum->setColor(Color3B(0, 200, 20));
453 _labelSpriteNum->setPosition(Vec2(s.width / 2, s.height - 130));
454 addChild(_labelSpriteNum);
455
457
458 labelCreate->setPosition(0, -20);
459 labelDestory->setPosition(0, -50);
460
461 parent->addChild(labelCreate);
462 parent->addChild(labelDestory);
463
464 doTest();
465}
466
468{
469 totalSprites = std::max(1, x);
470 std::stringstream ss;
471 ss << totalSprites << " sprites";
472 _labelSpriteNum->setString(ss.str());
473}
474
476{
477
478 DurationRecorder perf;
479 std::vector<std::string> predefineTextures = {
480 "Images/concave.png",
481 "Images/atlastest.png",
482 "Images/grossini_dance_atlas-mono.png",
483 "Images/HelloWorld.png",
484 "Images/background1.png",
485 "Images/background2.png",
486 "Images/stone.png",
487 "Images/issue_17116.png",
488 "Images/sprite_polygon_crash.png",
489 "Images/bitmapFontTest3.png",
490 "Images/cocos-html5.png",
491 "Images/Fog.png",
492 "Images/poly_test_textures.png",
493 "Images/powered.png",
494 "Images/bug14017.png",
495 "Images/test-rgba1.png",
496 "Images/grossinis_heads.png",
497 "Images/cocos2dbanner.png"
498 };
499
500
501 std::vector<Sprite*> spriteCache;
502 spriteCache.reserve(totalSprites);
503
505
506 for (int i=0; i< totalSprites; ++i)
507 {
508 auto* sprite = new Sprite();
509 if(sprite == nullptr )
510 {
511 break;
512 }
513 if(!sprite->initWithFile(predefineTextures[i % predefineTextures.size()]))
514 {
515 delete sprite;
516 break;
517 }
518 spriteCache.push_back(sprite);
519 }
520
521 auto creationDuration = perf.endTick(KEY_CREATION);
523
524 for (int i=0; i< totalSprites; ++i)
525 {
526 spriteCache[i]->release();
527 }
528 auto destroyDuration = perf.endTick(KEY_DESTROYATION);
529 std::stringstream ss;
530 auto t1_ms = creationDuration * 1.0 / 1000000;
531 ss << "Create "<< spriteCache.size() << " sprites takes " << t1_ms<< " ms, " << (int64_t)(spriteCache.size() * 1000 / t1_ms) << " sprites per second!";
532 labelCreate->setString(ss.str());
533
534 if(t1_ms < 100) {
535 suggestDelta =(int) (0.5 * totalSprites);
536 } else if (t1_ms < 1000) {
537 suggestDelta =(int) (0.2 * totalSprites);
538 } else if(t1_ms) {
539 suggestDelta =(int) (0.1 * totalSprites);
540 }
541
542 suggestDelta = suggestDelta < 1000 ? 1000 : suggestDelta - suggestDelta % 1000;
543
544 ss.str("");
545 auto t2_ms = destroyDuration * 1.0 / 1000000;
546 ss << "Destroy "<< spriteCache.size() << " sprites takes " << t2_ms<< " ms, " << (int64_t)(spriteCache.size() * 1000 / t2_ms) << " sprites per second!" ;
547 labelDestory->setString(ss.str());
548
549 spriteCache.clear();
550}
551
553{
555 doTest();
556}
557
559{
561 doTest();
562}
563
565{
566
567}
568
569std::string SpriteCreation::title() const
570{
571 return "Sprite Creation";
572}
573
574std::string SpriteCreation::subtitle() const
575{
576#if defined(COCOS2D_DEBUG) && COCOS2D_DEBUG == 1
577 return "In debug mode";
578#else
579 return "In release mode";
580#endif
581}
582
583
585{
586 Size s = Director::getInstance()->getWinSize();
587 Node* parent = Node::create();
588 parent->setPosition(0,0);
589 addChild(parent);
590
591 for (int i=0; i< Renderer::VBO_SIZE / 3.9; ++i)
592 {
593 Sprite* sprite = Sprite::create("Images/grossini_dance_01.png");
594 sprite->setScale(0.1f, 0.1f);
595 float x = ((float)std::rand()) /RAND_MAX;
596 float y = ((float)std::rand()) /RAND_MAX;
597 sprite->setPosition(Vec2(x * s.width, y * s.height));
598 parent->addChild(sprite);
599 }
600}
601
603{
604
605}
606
607std::string VBOFullTest::title() const
608{
609 return "New Renderer";
610}
611
612std::string VBOFullTest::subtitle() const
613{
614 return "VBO full Test, everything should render normally";
615}
616
618{
619 Size s = Director::getInstance()->getWinSize();
620 Vec2 left(s.width / 4, s.height / 2);
621 Vec2 right(s.width / 4 * 3, s.height / 2);
622
623 auto sp1 = Sprite::create("Images/grossini.png");
624 sp1->setPosition(left);
625 auto move1 = MoveBy::create(1, Vec2(s.width/2, 0.0f));
626 auto seq1 = RepeatForever::create(Sequence::create(move1, move1->reverse(), nullptr));
627 addChild(sp1);
628 sp1->runAction(seq1);
629 auto sp2 = Sprite::create("Images/grossinis_sister1.png");
630 sp2->setPosition(right);
631 auto move2 = MoveBy::create(1, Vec2(-s.width/2, 0.0f));
632 auto seq2 = RepeatForever::create(Sequence::create(move2, move2->reverse(), nullptr));
633 addChild(sp2);
634 sp2->runAction(seq2);
635
636 auto label1 = Label::createWithTTF(TTFConfig("fonts/arial.ttf"), "capture all");
637 auto mi1 = MenuItemLabel::create(label1, CC_CALLBACK_1(CaptureScreenTest::onCaptured, this));
638 auto menu = Menu::create(mi1, nullptr);
639 addChild(menu);
640 menu->setPosition(s.width / 2, s.height / 4);
641
642 _filename = "";
643}
644
646{
647 Director::getInstance()->getTextureCache()->removeTextureForKey(_filename);
648}
649
650std::string CaptureScreenTest::title() const
651{
652 return "New Renderer";
653}
654
656{
657 return "Capture screen test, press the menu items to capture the screen";
658}
659
661{
662 Director::getInstance()->getTextureCache()->removeTextureForKey(_filename);
663 removeChildByTag(childTag);
664 _filename = "CaptureScreenTest.png";
665 // retain it to avoid crash caused by invoking afterCaptured
666 this->retain();
667 utils::captureScreen(CC_CALLBACK_2(CaptureScreenTest::afterCaptured, this), _filename);
668}
669
670void CaptureScreenTest::afterCaptured(bool succeed, const std::string& outputFile)
671{
672 if (succeed)
673 {
674 auto sp = Sprite::create(outputFile);
675 addChild(sp, 0, childTag);
676 Size s = Director::getInstance()->getWinSize();
677 sp->setPosition(s.width / 2, s.height / 2);
678 sp->setScale(0.25);
679 _filename = outputFile;
680 }
681 else
682 {
683 log("Capture screen failed.");
684 }
685
686 // release it since it is retained in `CaptureScreenTest::onCaptured()`
687 this->release();
688}
689
691{
692 Size s = Director::getInstance()->getWinSize();
693 Vec2 left(s.width / 4, s.height / 2);
694 Vec2 right(s.width / 4 * 3, s.height / 2);
695
696 auto sp1 = Sprite::create("Images/grossini.png");
697 sp1->setPosition(left);
698 auto move1 = MoveBy::create(1, Vec2(s.width / 2, 0.0f));
699 auto seq1 = RepeatForever::create(Sequence::create(move1, move1->reverse(), nullptr));
700 addChild(sp1);
701 sp1->runAction(seq1);
702 auto sp2 = Sprite::create("Images/grossinis_sister1.png");
703 sp2->setPosition(right);
704 auto move2 = MoveBy::create(1, Vec2(-s.width / 2, 0.0f));
705 auto seq2 = RepeatForever::create(Sequence::create(move2, move2->reverse(), nullptr));
706 addChild(sp2);
707 sp2->runAction(seq2);
708
709 auto label1 = Label::createWithTTF(TTFConfig("fonts/arial.ttf"), "capture this scene");
710 auto mi1 = MenuItemLabel::create(label1, CC_CALLBACK_1(CaptureNodeTest::onCaptured, this));
711 auto menu = Menu::create(mi1, nullptr);
712 addChild(menu);
713 menu->setPosition(s.width / 2, s.height / 4);
714
715 _filename = "";
716}
717
719{
720 Director::getInstance()->getTextureCache()->removeTextureForKey(_filename);
721}
722
723std::string CaptureNodeTest::title() const
724{
725 return "New Renderer";
726}
727
728std::string CaptureNodeTest::subtitle() const
729{
730 return "Capture node test, press the menu items to capture this scene with scale 0.5";
731}
732
734{
735 Director::getInstance()->getTextureCache()->removeTextureForKey(_filename);
736 removeChildByTag(childTag);
737
738 _filename = FileUtils::getInstance()->getWritablePath() + "/CaptureNodeTest.png";
739
740 // capture this
741 auto callback = [&](Image* image){
742 // create a sprite with the captured image directly
743 auto sp = Sprite::createWithTexture(Director::getInstance()->getTextureCache()->addImage(image, _filename));
744 addChild(sp, 0, childTag);
745 Size s = Director::getInstance()->getWinSize();
746 sp->setPosition(s.width / 2, s.height / 2);
747
748 // store to disk
749 image->saveToFile(_filename);
750
751 // release the captured image
752 image->release();
753 };
754
755 auto callbackFunction = std::bind(callback, std::placeholders::_1);
756 utils::captureNode(this, callbackFunction, 0.5);
757}
758
760{
761 Size s = Director::getInstance()->getWinSize();
762 auto fastmap = cocos2d::FastTMXTiledMap::create("TileMaps/orthogonal-test2.tmx");
763 this->addChild(fastmap);
764 for (int i = 0; i < 30; i++) {
765 auto sprite = Sprite::create("Images/grossini.png");
766 sprite->setPosition(s.width/2 + s.width/10 * i, s.height/2);
767 this->addChild(sprite);
768 auto label = Label::createWithTTF(TTFConfig("fonts/arial.ttf"), "Label");
769 label->setPosition(s.width/2 + s.width/10 * i, s.height/2);
770 this->addChild(label);
771 }
772 this->scheduleOnce([=](float){
773 auto camera = Director::getInstance()->getRunningScene()->getCameras().front();
774 auto move = MoveBy::create(2.0f, Vec2(2 * s.width, 0.0f));
775 camera->runAction(Sequence::create(move, move->reverse(),nullptr));
776 }, 1.0f, "lambda-autoculling-bug");
777}
778
779std::string BugAutoCulling::title() const
780{
781 return "Bug-AutoCulling";
782}
783
784std::string BugAutoCulling::subtitle() const
785{
786 return "Moving the camera to the right instead of moving the layer";
787}
788
789//
790// RendererBatchQuadTri
791//
792
794{
795 Size s = Director::getInstance()->getWinSize();
796
797 for (int i=0; i<250; i++)
798 {
799 int x = CCRANDOM_0_1() * s.width;
800 int y = CCRANDOM_0_1() * s.height;
801
802 auto label = LabelAtlas::create("This is a label", "fonts/tuffy_bold_italic-charmap.plist");
803 label->setColor(Color3B::RED);
804 label->setPosition(Vec2(x,y));
805 addChild(label);
806
807 auto sprite = Sprite::create("fonts/tuffy_bold_italic-charmap.png");
808 sprite->setTextureRect(Rect(0.0f,0.0f,100.0f,100.0f));
809 sprite->setPosition(Vec2(x,y));
810 sprite->setColor(Color3B::BLUE);
811 addChild(sprite);
812 }
813}
814
816{
817 return "RendererBatchQuadTri";
818}
819
821{
822 return "QuadCommand and TriangleCommands are batched together";
823}
824
825
826//
827//
828// RendererUniformBatch
829//
830
832{
833 Size s = Director::getInstance()->getWinSize();
834
835 auto blurState = createBlurProgramState();
836 auto sepiaState = createSepiaProgramState();
837
838 auto x_inc = s.width / 20;
839 auto y_inc = s.height / 6;
840
841 for (int y=0; y<6; ++y)
842 {
843 for (int x=0; x<20; ++x)
844 {
845 auto sprite = Sprite::create("Images/grossini.png");
846 sprite->setPosition(Vec2(x * x_inc, y * y_inc));
847 sprite->setScale(0.4);
848 addChild(sprite);
849
850 if (y>=4) {
851 sprite->setProgramState(sepiaState);
852 } else if(y>=2) {
853 sprite->setProgramState(blurState);
854 }
855 }
856 }
857}
858
859cocos2d::backend::ProgramState* RendererUniformBatch::createBlurProgramState()
860{
861 const std::string shaderName("Shaders/example_Blur.fsh");
862 // outline shader
863 auto fileUtiles = FileUtils::getInstance();
864 auto fragmentFullPath = fileUtiles->fullPathForFilename(shaderName);
865 auto fragSource = fileUtiles->getStringFromFile(fragmentFullPath);
866 auto program = backend::Device::getInstance()->newProgram(positionTextureColor_vert, fragSource.c_str());
867 auto programState = new backend::ProgramState(program);
868 programState->autorelease();
869 CC_SAFE_RELEASE(program);
870
871 backend::UniformLocation loc = programState->getUniformLocation("resolution");
872 auto resolution = Vec2(85, 121);
873 programState->setUniform(loc, &resolution, sizeof(resolution));
874
875 loc = programState->getUniformLocation("blurRadius");
876 float blurRadius = 10.0f;
877 programState->setUniform(loc, &blurRadius, sizeof(blurRadius));
878
879 loc = programState->getUniformLocation("sampleNum");
880 float sampleNum = 5.0f;
881 programState->setUniform(loc, &sampleNum, sizeof(sampleNum));
882
883 return programState;
884}
885
886cocos2d::backend::ProgramState* RendererUniformBatch::createSepiaProgramState()
887{
888 const std::string shaderName("Shaders/example_Sepia.fsh");
889
890 // outline shader
891 auto fileUtiles = FileUtils::getInstance();
892 auto fragmentFullPath = fileUtiles->fullPathForFilename(shaderName);
893 auto fragSource = fileUtiles->getStringFromFile(fragmentFullPath);
894 auto program = backend::Device::getInstance()->newProgram(positionTextureColor_vert, fragSource.c_str());
895 auto programState = new backend::ProgramState(program);
896 programState->autorelease();
897 CC_SAFE_RELEASE(program);
898 return programState;
899}
900
902{
903 return "RendererUniformBatch";
904}
905
907{
908 return "Only 9 draw calls should appear";
909}
910
911
915
917{
918 Size s = Director::getInstance()->getWinSize();
919
920 auto blurState = createBlurProgramState();
921 auto sepiaState = createSepiaProgramState();
922
923 auto x_inc = s.width / 20;
924 auto y_inc = s.height / 6;
925
926 for (int y=0; y<6; ++y)
927 {
928 for (int x=0; x<20; ++x)
929 {
930 auto sprite = Sprite::create("Images/grossini.png");
931 sprite->setPosition(Vec2(x * x_inc, y * y_inc));
932 sprite->setScale(0.4);
933 addChild(sprite);
934
935 auto r = CCRANDOM_0_1();
936 if (r < 0.33)
937 sprite->setProgramState(sepiaState);
938 else if (r < 0.66)
939 sprite->setProgramState(blurState);
940 }
941 }
942}
943
945{
946 const std::string shaderName("Shaders/example_Blur.fsh");
947
948 // outline shader
949 auto fileUtiles = FileUtils::getInstance();
950 auto fragmentFullPath = fileUtiles->fullPathForFilename(shaderName);
951 auto fragSource = fileUtiles->getStringFromFile(fragmentFullPath);
952 auto program = backend::Device::getInstance()->newProgram(positionTextureColor_vert, fragSource.c_str());
953 auto programState = new backend::ProgramState(program);
954 programState->autorelease();
955 CC_SAFE_RELEASE(program);
956
957 backend::UniformLocation loc = programState->getUniformLocation("resolution");
958 auto resolution = Vec2(85, 121);
959 programState->setUniform(loc, &resolution, sizeof(resolution));
960
961 loc = programState->getUniformLocation("blurRadius");
962 float blurRadius = 10.0f;
963 programState->setUniform(loc, &blurRadius, sizeof(blurRadius));
964
965 loc = programState->getUniformLocation("sampleNum");
966 float sampleNum = 5.0f;
967 programState->setUniform(loc, &sampleNum, sizeof(sampleNum));
968
969 return programState;
970}
971
973{
974 const std::string shaderName("Shaders/example_Sepia.fsh");
975
976 // outline shader
977 auto fileUtiles = FileUtils::getInstance();
978 auto fragmentFullPath = fileUtiles->fullPathForFilename(shaderName);
979 auto fragSource = fileUtiles->getStringFromFile(fragmentFullPath);
980 auto program = backend::Device::getInstance()->newProgram(positionTextureColor_vert, fragSource.c_str());
981 auto programState = new backend::ProgramState(program);
982 programState->autorelease();
983 CC_SAFE_RELEASE(program);
984 return programState;
985}
986
988{
989 return "RendererUniformBatch 2";
990}
991
993{
994 return "Mixing different shader states should work ok";
995}
996
998{
999 Size s = Director::getInstance()->getWinSize();
1000 _spritesAnchor = Node::create();
1001 _spritesAnchor->setPosition(0, 0);
1002 addChild(_spritesAnchor);
1003
1004
1005 _totalSprites = Label::createWithTTF(TTFConfig("fonts/arial.ttf"), "sprites");
1006 _totalSprites->setColor(Color3B::YELLOW);
1007 _totalSprites->enableOutline(Color4B::RED, 2);
1008 _totalSprites->setPosition(s.width/2, s.height/2);
1009
1010 addChild(_totalSprites);
1011
1012 scheduleUpdate();
1013}
1014
1016{
1017
1018 Size s = Director::getInstance()->getWinSize();
1019 Sprite* sprite = nullptr;
1020 if (_spriteIndex % 2 == 0)
1021 {
1022 sprite = Sprite::create("Images/grossini_dance_05.png");
1023 }
1024 else
1025 {
1026 sprite = Sprite::create("Images/grossini_dance_01.png");
1027 }
1028
1029 if (!sprite) return;
1030 auto r = rand_0_1() * 0.6 + 0.2;
1031 sprite->setScale(r, r);
1032 float x = ((float)std::rand()) / RAND_MAX;
1033 float y = ((float)std::rand()) / RAND_MAX;
1034 sprite->runAction(RepeatForever::create(RotateBy::create(1, 45)));
1035
1036 sprite->setPosition(Vec2(x * s.width, y * s.height));
1037 _spritesAnchor->addChild(sprite);
1038
1039 _spriteIndex++;
1040 std::stringstream ss;
1041 ss << _spriteIndex << " sprites";
1042 _totalSprites->setString(ss.str());
1043}
1044
1046{
1047
1048 if( dt <= 1.0f / 28.0f && dt >= 1.0f/ 31.0f)
1049 {
1050 _around30fps.hit();
1051 }
1052 else
1053 {
1055 }
1056
1057 _maDt = 0.7f * _maDt + 0.3f * dt;
1058 _rmaDt = 0.5f * _rmaDt + 0.5f * dt;
1059 if(_maDt <= DEST_DT_30FPS) {
1060 _contSlow.cancel();
1061 _contFast.hit();
1062 if(_contFast.ok()){
1063 auto t2 = DEST_DT_30FPS - _rmaDt;
1064 auto delta = (int)(t2 / _rmaDt * _spriteIndex * 0.1);
1065 delta =std::min(20, std::max(1, delta));
1066 for(int i =0 ;i< delta; i++) {
1067 createSprite();
1068 }
1069 }
1070 }else{
1071 _contSlow.hit();
1072 _contFast.cancel();
1073 }
1074
1075 if(_contSlow.ok() || _around30fps.ok())
1076 {
1077 unscheduleUpdate();
1078 std::stringstream ss;
1079 ss << _spriteIndex << " sprites, DONE!";
1080 _totalSprites->setString(ss.str());
1081 _totalSprites->setScale(1.2);
1082 }
1083}
1084
1086{
1087
1088}
1089
1090std::string NonBatchSprites::title() const
1091{
1092 return "Non Batched Sprites";
1093}
1094
1095std::string NonBatchSprites::subtitle() const
1096{
1097#if defined(COCOS2D_DEBUG) && COCOS2D_DEBUG == 1
1098 return "DEBUG: simulate lots of sprites, drop to 30 fps";
1099#else
1100 return "RELEASE: simulate lots of sprites, drop to 30 fps";
1101#endif
1102}
1103
#define ADD_TEST_CASE(__className__)
Definition: BaseTest.h:211
@ kTagContentNode
@ kTagClipperNode
#define KEY_CREATION
#define KEY_DESTROYATION
USING_NS_CC
virtual std::string title() const override
virtual std::string subtitle() const override
static const int childTag
virtual std::string subtitle() const override
std::string _filename
virtual std::string title() const override
void onCaptured(cocos2d::Ref *)
void afterCaptured(bool succeed, const std::string &outputFile)
static const int childTag
void onCaptured(cocos2d::Ref *)
virtual std::string title() const override
std::string _filename
virtual std::string subtitle() const override
int64_t now() const
int endTick(const std::string &key)
std::map< std::string, int64_t > _durations
void startTick(const std::string &key)
virtual std::string title() const override
virtual ~GroupCommandTest()
virtual std::string subtitle() const override
virtual std::string subtitle() const override
virtual std::string title() const override
void onTouchesMoved(const std::vector< cocos2d::Touch * > &touches, cocos2d::Event *event)
void onTouchesEnded(const std::vector< cocos2d::Touch * > &touches, cocos2d::Event *event)
virtual std::string subtitle() const override
void onTouchesBegan(const std::vector< cocos2d::Touch * > &touches, cocos2d::Event *event)
cocos2d::Vec2 _lastPoint
virtual std::string title() const override
cocos2d::Vec2 _lastPos
virtual std::string title() const override
void onTouchMoved(cocos2d::Touch *touch, cocos2d::Event *event)
virtual std::string subtitle() const override
virtual ~NewCullingTest()
bool onTouchBegan(cocos2d::Touch *touch, cocos2d::Event *event)
virtual ~NewDrawNodeTest()
virtual std::string subtitle() const override
virtual std::string title() const override
virtual std::string subtitle() const override
virtual std::string title() const override
void onTouchesEnded(const std::vector< cocos2d::Touch * > &touches, cocos2d::Event *event)
void createNewSpriteTest()
virtual ~NewSpriteTest()
virtual void update(float dt) override
virtual std::string title() const override
virtual ~NonBatchSprites()
virtual std::string subtitle() const override
const float DEST_DT_30FPS
cocos2d::Label * _totalSprites
virtual std::string title() const override
virtual std::string subtitle() const override
virtual std::string title() const override
cocos2d::backend::ProgramState * createSepiaProgramState()
virtual std::string subtitle() const override
cocos2d::backend::ProgramState * createBlurProgramState()
virtual std::string title() const override
virtual std::string subtitle() const override
cocos2d::backend::ProgramState * createSepiaProgramState()
cocos2d::backend::ProgramState * createBlurProgramState()
virtual std::string title() const override
void addSpritesCallback(Ref *)
void delSpritesCallback(Ref *)
void updateSpriteCountLabel(int x)
cocos2d::Label * _labelSpriteNum
virtual std::string subtitle() const override
cocos2d::Label * labelCreate
virtual ~SpriteCreation()
cocos2d::Label * labelDestory
static SpriteInGroupCommand * create(const std::string &filename)
virtual void draw(Renderer *renderer, const Mat4 &transform, uint32_t flags) override
GroupCommand _spriteWrapperCommand
virtual std::string subtitle() const override
virtual std::string title() const override
virtual ~VBOFullTest()