7
// don't use this code! It lacks many checks and is for testing
9
// based on code and media from SuperTuxKart
10
class ScalableFont : public gui::IGUIFontBitmap
15
irr::core::stringc m_file_name;
26
std::map<int /* texture file ID */, TextureInfo> m_texture_files;
28
void lazyLoadTexture(int texID)
30
const bool mipmap = Driver->getTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS);
31
Driver->setTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS, true);
33
SpriteBank->setTexture(texID, Driver->getTexture( m_texture_files[texID].m_file_name ));
34
// set previous mip-map+filter state
35
Driver->setTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS, mipmap);
37
// couldn't load texture, abort.
38
if (!SpriteBank->getTexture(texID))
44
// colorkey texture rather than alpha channel?
45
if (! m_texture_files[texID].m_has_alpha)
47
Driver->makeColorKeyTexture(SpriteBank->getTexture(texID), core::position2di(0,0));
51
void doReadXmlFile(io::IXMLReader* xml)
55
if (io::EXN_ELEMENT == xml->getNodeType())
57
if (core::stringw(L"include") == xml->getNodeName())
59
core::stringc filename = xml->getAttributeValue(L"file");
60
io::IXMLReader* included = Environment->getFileSystem()->createXMLReader(filename.c_str());
63
doReadXmlFile(included);
67
else if (core::stringw(L"Texture") == xml->getNodeName())
70
core::stringc filename = xml->getAttributeValue(L"filename");
71
core::stringc fn = filename;
72
u32 i = (u32)xml->getAttributeValueAsInt(L"index");
75
if (xml->getAttributeValue(L"scale"))
76
scale = xml->getAttributeValueAsFloat(L"scale");
77
//std::cout << "scale = " << scale << std::endl;
79
core::stringw alpha = xml->getAttributeValue(L"hasAlpha");
81
//std::cout << "---- Adding font texture " << fn.c_str() << "; alpha=" << alpha.c_str() << std::endl;
84
// make sure the sprite bank has enough textures in it
85
while (i+1 > SpriteBank->getTextureCount())
87
SpriteBank->addTexture(NULL);
91
info.m_file_name = fn;
92
info.m_has_alpha = (alpha == core::stringw("true"));
95
m_texture_files[i] = info;
97
else if (core::stringw(L"c") == xml->getNodeName())
99
// adding a character to this font
101
gui::SGUISpriteFrame f;
103
core::rect<s32> rectangle;
105
a.underhang = xml->getAttributeValueAsInt(L"u");
106
a.overhang = xml->getAttributeValueAsInt(L"o");
107
a.spriteno = SpriteBank->getSprites().size();
108
s32 texno = xml->getAttributeValueAsInt(L"i");
111
core::stringc rectstr = xml->getAttributeValue(L"r");
112
wchar_t ch = xml->getAttributeValue(L"c")[0];
114
const c8 *c = rectstr.c_str();
117
while (*c >= '0' && *c <= '9')
123
rectangle.UpperLeftCorner.X = val;
124
while (*c == L' ' || *c == L',') c++;
127
while (*c >= '0' && *c <= '9')
133
rectangle.UpperLeftCorner.Y = val;
134
while (*c == L' ' || *c == L',') c++;
137
while (*c >= '0' && *c <= '9')
143
rectangle.LowerRightCorner.X = val;
144
while (*c == L' ' || *c == L',') c++;
147
while (*c >= '0' && *c <= '9')
153
rectangle.LowerRightCorner.Y = val;
155
CharacterMap[ch] = Areas.size();
158
f.rectNumber = SpriteBank->getPositions().size();
159
f.textureNumber = texno;
161
// add frame to sprite
162
s.Frames.push_back(f);
165
// add rectangle to sprite bank
166
SpriteBank->getPositions().push_back(rectangle);
167
a.width = rectangle.getWidth();
169
// add sprite to sprite bank
170
SpriteBank->getSprites().push_back(s);
172
// add character to font
183
ScalableFont* m_fallback_font;
184
float m_fallback_font_scale;
185
int m_fallback_kerning_width;
188
ScalableFont(gui::IGUIEnvironment *env, const io::path& filename)
189
: Driver(0), SpriteBank(0), Environment(env), WrongCharacter(0),
190
MaxHeight(0), GlobalKerningWidth(0), GlobalKerningHeight(0)
193
setDebugName("ScalableFont");
196
m_fallback_font = NULL;
197
m_fallback_kerning_width = 0;
198
m_fallback_font_scale = 1.0f;
200
m_black_border = false;
204
// don't grab environment, to avoid circular references
205
Driver = Environment->getVideoDriver();
207
SpriteBank = Environment->addEmptySpriteBank(filename);
215
setInvisibleCharacters ( L" " );
217
io::IXMLReader* reader = env->getFileSystem()->createXMLReader(filename.c_str());
223
assert(Areas.size() > 0);
227
virtual ~ScalableFont()
235
//! loads a font from an XML file
236
bool load(io::IXMLReader* xml)
244
WrongCharacter = getAreaIDFromCharacter(L' ', NULL);
248
for(wchar_t c='0'; c<='9'; c++)
250
SFontArea a = getAreaFromCharacter(c, NULL);
251
if (a.overhang > m_max_digit_area.overhang ) m_max_digit_area.overhang = a.overhang;
252
if (a.underhang > m_max_digit_area.underhang) m_max_digit_area.underhang = a.underhang;
253
if (a.width > m_max_digit_area.width) m_max_digit_area.width = a.width;
255
m_max_digit_area.overhang = 0;
256
m_max_digit_area.underhang=0;
259
//! draws an text and clips it to the specified rectangle if wanted
260
virtual void draw(const core::stringw& text, const core::rect<s32>& position,
261
video::SColor color, bool hcenter=false,
262
bool vcenter=false, const core::rect<s32>* clip=0)
266
core::position2d<s32> offset = position.UpperLeftCorner;
267
core::dimension2d<s32> text_dimension;
269
// When we use the "tab" hack, disable right-alignment, it messes up everything
270
// bool has_tab = (text.findFirst(L'\t') != -1);
271
// ---- collect character locations
272
const unsigned int text_size = text.size();
273
core::array<s32> indices(text_size);
274
core::array<core::position2di> offsets(text_size);
275
core::array<bool> fallback;
276
fallback.set_used(text_size);
278
for (u32 i = 0; i<text_size; i++)
282
//hack: one tab character is supported, it moves the cursor to the middle of the area
285
offset.X = position.UpperLeftCorner.X + position.getWidth()/2;
289
if (c == L'\r' || // Windows breaks
290
c == L'\n') // Unix breaks
292
if (c==L'\r' && text[i+1]==L'\n')
294
offset.Y += (int)(MaxHeight*m_scale);
295
offset.X = position.UpperLeftCorner.X;
297
offset.X += (position.getWidth() - text_dimension.Width) >> 1;
301
bool use_fallback_font = false;
302
const SFontArea &area = getAreaFromCharacter(c, &use_fallback_font);
303
fallback[i] = use_fallback_font;
304
offset.X += area.underhang;
305
offsets.push_back(offset);
306
// Invisible character. add something to the array anyway so that
307
// indices from the various arrays remain in sync
308
indices.push_back((Invisible.findFirst(c) < 0) ? (int)area.spriteno
310
offset.X += getCharWidth(area, fallback[i]);
313
// ---- do the actual rendering
314
const int indiceAmount = indices.size();
315
core::array< gui::SGUISprite >& sprites = SpriteBank->getSprites();
316
core::array< core::rect<s32> >& positions = SpriteBank->getPositions();
317
core::array< gui::SGUISprite >* fallback_sprites;
318
core::array< core::rect<s32> >* fallback_positions;
319
if (m_fallback_font!=NULL)
321
fallback_sprites = &m_fallback_font->SpriteBank->getSprites();
322
fallback_positions = &m_fallback_font->SpriteBank->getPositions();
326
fallback_sprites = NULL;
327
fallback_positions = NULL;
330
video::IVideoDriver* driver = Environment->getVideoDriver();
331
const int spriteAmount = sprites.size();
332
for (int n=0; n<indiceAmount; n++)
334
const int spriteID = indices[n];
335
if (!fallback[n] && (spriteID < 0 || spriteID >= spriteAmount))
337
if (indices[n] == -1)
340
//assert(sprites[spriteID].Frames.size() > 0);
342
const int texID = (fallback[n] ?
343
(*fallback_sprites)[spriteID].Frames[0].textureNumber :
344
sprites[spriteID].Frames[0].textureNumber);
346
core::rect<s32> source = (fallback[n] ?
347
(*fallback_positions)[(*fallback_sprites)[spriteID].Frames[0].rectNumber] :
348
positions[sprites[spriteID].Frames[0].rectNumber]);
350
const TextureInfo& info = (fallback[n] ?
351
(*(m_fallback_font->m_texture_files.find(texID))).second :
352
(*(m_texture_files.find(texID))).second);
353
float char_scale = info.m_scale;
355
core::dimension2d<s32> size = source.getSize();
357
float scale = (fallback[n] ? m_scale*m_fallback_font_scale : m_scale);
358
size.Width = (int)(size.Width * scale * char_scale);
359
size.Height = (int)(size.Height * scale * char_scale);
361
// align vertically if character is smaller
362
int y_shift = (size.Height < MaxHeight*m_scale ? (int)((MaxHeight*m_scale - size.Height)/2.0f) : 0);
364
core::rect<s32> dest(offsets[n] + core::position2di(0, y_shift), size);
366
video::SColor colors[] = {color, color, color, color};
368
video::ITexture* texture = (fallback[n] ?
369
m_fallback_font->SpriteBank->getTexture(texID) :
370
SpriteBank->getTexture(texID) );
374
// perform lazy loading
378
m_fallback_font->lazyLoadTexture(texID);
379
texture = m_fallback_font->SpriteBank->getTexture(texID);
383
lazyLoadTexture(texID);
384
texture = SpriteBank->getTexture(texID);
389
continue; // no such character
396
video::SColor black(color.getAlpha(),0,0,0);
397
video::SColor black_colors[] = {black, black, black, black};
399
for (int x_delta=-2; x_delta<=2; x_delta++)
401
for (int y_delta=-2; y_delta<=2; y_delta++)
403
if (x_delta == 0 || y_delta == 0) continue;
404
driver->draw2DImage(texture,
405
dest + core::position2d<s32>(x_delta, y_delta),
416
static video::SColor orange(color.getAlpha(), 255, 100, 0);
417
static video::SColor yellow(color.getAlpha(), 255, 220, 15);
418
video::SColor title_colors[] = {yellow, orange, orange, yellow};
419
driver->draw2DImage(texture,
427
driver->draw2DImage(texture,
437
//! returns the dimension of a text
438
virtual core::dimension2d<u32> getDimension(const wchar_t* text) const
440
assert(Areas.size() > 0);
442
core::dimension2d<u32> dim(0, 0);
443
core::dimension2d<u32> thisLine(0, (int)(MaxHeight*m_scale));
445
for (const wchar_t* p = text; *p; ++p)
447
if (*p == L'\r' || // Windows breaks
448
*p == L'\n') // Unix breaks
450
if (*p==L'\r' && p[1] == L'\n') // Windows breaks
452
dim.Height += thisLine.Height;
453
if (dim.Width < thisLine.Width)
454
dim.Width = thisLine.Width;
459
bool fallback = false;
460
const SFontArea &area = getAreaFromCharacter(*p, &fallback);
462
thisLine.Width += area.underhang;
464
thisLine.Width += getCharWidth(area, fallback);
467
dim.Height += thisLine.Height;
468
if (dim.Width < thisLine.Width) dim.Width = thisLine.Width;
470
// std::cout << "ScalableFont::getDimension returns : " << dim.Width << ", " << dim.Height << " --> ";
472
dim.Width = (int)(dim.Width + 0.9f); // round up
473
dim.Height = (int)(dim.Height + 0.9f);
475
//std::cout << dim.Width << ", " << dim.Height << std::endl;
479
//! Calculates the index of the character in the text which is on a specific position.
480
virtual s32 getCharacterFromPos(const wchar_t* text, s32 pixel_x) const
487
const SFontArea& a = Areas[getAreaIDFromCharacter(text[idx], NULL)];
489
x += a.width + a.overhang + a.underhang + GlobalKerningWidth;
499
//! Returns the type of this font
500
virtual gui::EGUI_FONT_TYPE getType() const { return gui::EGFT_BITMAP; }
502
//! set an Pixel Offset on Drawing ( scale position on width )
503
virtual void setKerningWidth (s32 kerning)
505
GlobalKerningWidth = kerning;
507
virtual void setKerningHeight (s32 kerning)
509
GlobalKerningHeight = kerning;
511
//! set an Pixel Offset on Drawing ( scale position on width )
512
virtual s32 getKerningWidth(const wchar_t* thisLetter=0, const wchar_t* previousLetter=0) const
514
s32 ret = GlobalKerningWidth;
518
ret += Areas[getAreaIDFromCharacter(*thisLetter, NULL)].overhang;
522
ret += Areas[getAreaIDFromCharacter(*previousLetter, NULL)].underhang;
528
virtual s32 getKerningHeight() const
530
return GlobalKerningHeight;
533
//! gets the sprite bank
534
virtual gui::IGUISpriteBank* getSpriteBank() const
539
//! returns the sprite number from a given character
540
virtual u32 getSpriteNoFromChar(const wchar_t *c) const
542
return Areas[getAreaIDFromCharacter(*c, NULL)].spriteno;
545
virtual void setInvisibleCharacters( const wchar_t *s )
554
SFontArea() : underhang(0), overhang(0), width(0), spriteno(0) {}
561
int getCharWidth(const SFontArea& area, const bool fallback) const
563
core::array< gui::SGUISprite >& sprites = SpriteBank->getSprites();
564
core::array< gui::SGUISprite >* fallback_sprites = (m_fallback_font != NULL ?
565
&m_fallback_font->SpriteBank->getSprites() :
568
const int texID = (fallback ?
569
(*fallback_sprites)[area.spriteno].Frames[0].textureNumber :
570
sprites[area.spriteno].Frames[0].textureNumber);
572
const TextureInfo& info = (fallback ?
573
(*(m_fallback_font->m_texture_files.find(texID))).second :
574
(*(m_texture_files.find(texID))).second);
575
const float char_scale = info.m_scale;
577
//std::cout << "area.spriteno=" << area.spriteno << ", char_scale=" << char_scale << std::endl;
580
return (int)(((area.width + area.overhang)*m_fallback_font_scale + m_fallback_kerning_width) * m_scale * char_scale);
582
return (int)((area.width + area.overhang + GlobalKerningWidth) * m_scale * char_scale);
584
s32 getAreaIDFromCharacter(const wchar_t c, bool* fallback_font) const
586
std::map<wchar_t, s32>::const_iterator n = CharacterMap.find(c);
587
if (n != CharacterMap.end())
589
if (fallback_font != NULL)
590
*fallback_font = false;
593
else if (m_fallback_font != NULL && fallback_font != NULL)
595
*fallback_font = true;
596
return m_fallback_font->getAreaIDFromCharacter(c, NULL);
600
// std::cout << "The font does not have this character : <" << (int)c << ">" << std::endl;
601
if (fallback_font != NULL)
602
*fallback_font = false;
603
return WrongCharacter;
606
const SFontArea &getAreaFromCharacter(const wchar_t c, bool* fallback_font) const
608
const int area_id = getAreaIDFromCharacter(c, fallback_font);
609
const bool use_fallback_font = (fallback_font && *fallback_font);
611
// Note: fallback_font can be NULL
612
return ( use_fallback_font ? m_fallback_font->Areas[area_id] : Areas[area_id]);
613
} // getAreaFromCharacter
616
// FIXME: should consider per-texture scaling
620
core::array< core::rect<s32> >& p = SpriteBank->getPositions();
622
for (u32 i=0; i<p.size(); ++i)
624
t = p[i].getHeight();
629
core::array<SFontArea> Areas;
630
/** The maximum values of all digits, used in monospace_digits. */
631
mutable SFontArea m_max_digit_area;
632
std::map<wchar_t, s32> CharacterMap;
633
video::IVideoDriver* Driver;
634
gui::IGUISpriteBank* SpriteBank;
635
gui::IGUIEnvironment* Environment;
638
s32 GlobalKerningWidth, GlobalKerningHeight;
640
core::stringw Invisible;
644
// The actual bug that was behind this issue was the combination of
645
// 2d rendering and mipmaps. The issue was reproduced using the special
646
// draw2dimage version, hence the name.
647
static bool draw2DImage4c(video::E_DRIVER_TYPE type)
649
IrrlichtDevice *device = createDevice(type, core::dimension2d<u32>(240, 120));
652
return true; // could not create selected driver.
654
video::IVideoDriver* driver = device->getVideoDriver();
656
if (!driver->queryFeature(video::EVDF_BILINEAR_FILTER))
658
device->closeDevice();
664
logTestString("Testing driver %ls\n", driver->getName());
666
driver->setTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS,true);
667
driver->setTextureCreationFlag(video::ETCF_OPTIMIZED_FOR_QUALITY,true);
669
video::ITexture* images = driver->getTexture("../media/2ddemo.png");
670
driver->makeColorKeyTexture(images, core::position2d<s32>(0,0));
672
core::rect<s32> imp1(349,15,385,78);
673
core::rect<s32> imp2(387,15,423,78);
675
// font cannot handle loading from sub-dirs
676
io::path cwd = device->getFileSystem()->getWorkingDirectory();
677
device->getFileSystem()->changeWorkingDirectoryTo("media");
679
ScalableFont* font = new ScalableFont(device->getGUIEnvironment(), "title_font.xml");
680
font->m_fallback_font_scale = 4.0f;
681
font->m_fallback_kerning_width = 15;
682
font->setKerningWidth(-18);
683
font->m_black_border = true;
686
Prepare a nicely filtering 2d render mode for special cases.
688
driver->getMaterial2D().UseMipMaps = true;
689
driver->getMaterial2D().TextureLayer[0].BilinearFilter = true;
692
driver->beginScene(true, true, video::SColor(255,120,102,136));
694
driver->enableMaterial2D();
696
// draw fire & dragons background world
697
driver->draw2DImage(images, core::position2di(),
698
core::rect<s32>(0,0,342,224), 0,
699
video::SColor(255,255,255,255), true);
702
driver->draw2DImage(images, core::position2d<s32>(114,75),
703
imp1, 0, video::SColor(255,255,255,255), true);
705
// draw second flying imp
706
driver->draw2DImage(images, core::position2d<s32>(220,55),
707
imp2, 0, video::SColor(255,255,255,255), true);
709
driver->draw2DImage(images, core::rect<s32>(10,10,108,48),
710
core::rect<s32>(354,87,442,118));
712
video::SColor colors[] = {0xff00ffff, 0xff00ffff, 0xffffff00, 0xffffff00};
713
driver->draw2DImage(images, core::recti(10,50,108,88),
714
core::recti(354,87,442,118), 0, colors, true);
716
font->draw( L"WXYZsSdDrRjJbB", core::rect<s32>(30,20,300,300),
717
video::SColor(255,255,255,255) );
719
driver->enableMaterial2D(false);
721
driver->draw2DImage(images, core::recti(10,90,108,128),
722
core::recti(354,87,442,118), 0, colors, true);
724
font->draw( L"WXYZsSdDrRjJbB", core::rect<s32>(30,60,300,400),
725
video::SColor(255,255,255,255) );
730
device->getFileSystem()->changeWorkingDirectoryTo(cwd);
732
// don't go under 99% as the difference is not very large
733
bool result = takeScreenshotAndCompareAgainstReference(driver, "-draw2DImage4cFilter.png");
735
device->closeDevice();
741
// This test renders a 3d scene and a gui on top of it. The GUI is
742
// filtered via 2dmaterial (blurred).
743
// TODO: Works only for OpenGL right now
744
static bool addBlend2d(video::E_DRIVER_TYPE type)
746
SIrrlichtCreationParameters params;
747
params.AntiAlias = 0;
749
params.WindowSize = core::dimension2d<u32>(160, 120);
750
params.DriverType = type;
752
IrrlichtDevice *device = createDeviceEx(params);
755
return true; // in case the driver type does not exist
757
video::IVideoDriver* driver = device->getVideoDriver();
758
scene::ISceneManager* smgr = device->getSceneManager();
760
if (!driver->queryFeature(video::EVDF_BILINEAR_FILTER))
762
device->closeDevice();
768
logTestString("Testing driver %ls\n", driver->getName());
770
scene::IAnimatedMesh* mesh = smgr->getMesh("../media/sydney.md2");
773
device->closeDevice();
778
scene::IAnimatedMeshSceneNode* node = smgr->addAnimatedMeshSceneNode( mesh );
782
node->setMaterialFlag(video::EMF_LIGHTING, false);
783
node->setMD2Animation(scene::EMAT_STAND);
784
node->setMaterialTexture( 0, driver->getTexture("../media/sydney.bmp") );
787
smgr->addCameraSceneNode(0, core::vector3df(0,30,-40), core::vector3df(0,5,0));
789
gui::IGUIEnvironment* env = device->getGUIEnvironment();
791
// create the toolbox window
792
gui::IGUIWindow* wnd = env->addWindow(core::rect<s32>(0,0,800,480),
793
false, L"Toolset", 0, 100);
795
// create tab control and tabs
796
gui::IGUITabControl* tab = env->addTabControl(
797
core::rect<s32>(2,20,800-602,480-7), wnd, true, true);
799
gui::IGUITab* t1 = tab->addTab(L"Config");
801
// add some edit boxes and a button to tab one
802
env->addImage(driver->getTexture("../media/tools.png"), core::vector2d<s32>(10,20), true, t1);
803
env->addStaticText(L"X:", core::rect<s32>(22,48,40,66), false, false, t1);
804
env->addEditBox(L"1.0", core::rect<s32>(40,46,130,66), true, t1, 201);
806
// quick scale buttons
807
env->addButton(core::rect<s32>(65,20,95,40), t1, 102, L"* 10");
808
env->addButton(core::rect<s32>(100,20,130,40), t1, 103, L"* 0.1");
811
video::SMaterial& material2D = driver->getMaterial2D();
812
for (unsigned int n=0; n<video::MATERIAL_MAX_TEXTURES; n++)
814
material2D.TextureLayer[n].BilinearFilter = true;
815
material2D.TextureLayer[n].TextureWrapU = video::ETC_CLAMP_TO_EDGE;
816
material2D.TextureLayer[n].TextureWrapV = video::ETC_CLAMP_TO_EDGE;
818
material2D.AntiAliasing=video::EAAM_FULL_BASIC;
820
driver->beginScene(true, true, video::SColor(255,100,101,140));
822
driver->enableMaterial2D();
824
driver->enableMaterial2D(false);
827
bool result = takeScreenshotAndCompareAgainstReference(driver, "-addBlend2D.png", 98.2f);
829
device->closeDevice();
835
// This test renders 4 times the same image. Two via IGUIImage, two via draw2DImage
836
// 3 of the 4 images are filtered via 2dmaterial and bilinear filter, only the one
837
// at the bottom left is not.
838
static bool moreFilterTests(video::E_DRIVER_TYPE type)
840
IrrlichtDevice* device = irr::createDevice(type, core::dimension2du(160,120));
844
video::IVideoDriver* driver = device->getVideoDriver();
845
gui::IGUIEnvironment* gui = device->getGUIEnvironment();
847
if (!driver->queryFeature(video::EVDF_BILINEAR_FILTER))
849
device->closeDevice();
855
logTestString("Testing driver %ls\n", driver->getName());
857
driver->setTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS, false);
858
video::ITexture* tex = driver->getTexture("../media/irrlichtlogo.jpg");
859
gui::IGUIImage* image = gui->addImage(core::recti(0,0,64,64));
860
image->setScaleImage(true);
861
image->setImage(tex);
862
image->setUseAlphaChannel(true);
863
driver->getMaterial2D().TextureLayer[0].BilinearFilter=true;
864
driver->getMaterial2D().TextureLayer[0].TrilinearFilter=true;
867
driver->beginScene(true, true, irr::video::SColor(255,255,255,255));
869
// all three logos should be with filtering
870
driver->enableMaterial2D();
872
driver->getMaterial2D().setTexture(0, 0);
873
driver->draw2DImage(tex, irr::core::rect<irr::s32>(64, 64, 128, 128), irr::core::rect<irr::s32>(0, 0, 88, 31));
875
driver->getMaterial2D().setTexture(0, tex);
876
driver->draw2DImage(tex, irr::core::rect<irr::s32>(64, 0, 128, 64), irr::core::rect<irr::s32>(0, 0, 88, 31));
880
// the next gui image should be without filter
881
driver->enableMaterial2D(false);
882
image->setRelativePosition(core::recti(0,64,64,128));
888
bool result = takeScreenshotAndCompareAgainstReference(driver, "-2dmatFilter.png");
890
device->closeDevice();
899
TestWithAllDrivers(addBlend2d);
900
TestWithAllDrivers(moreFilterTests);
901
TestWithAllDrivers(draw2DImage4c);