tcuTexture.hpp revision 6c307165131fb7249bb044fc79ff0c2747263b3d
1#ifndef _TCUTEXTURE_HPP
2#define _TCUTEXTURE_HPP
3/*-------------------------------------------------------------------------
4 * drawElements Quality Program Tester Core
5 * ----------------------------------------
6 *
7 * Copyright 2014 The Android Open Source Project
8 *
9 * Licensed under the Apache License, Version 2.0 (the "License");
10 * you may not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
12 *
13 *      http://www.apache.org/licenses/LICENSE-2.0
14 *
15 * Unless required by applicable law or agreed to in writing, software
16 * distributed under the License is distributed on an "AS IS" BASIS,
17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 * See the License for the specific language governing permissions and
19 * limitations under the License.
20 *
21 *//*!
22 * \file
23 * \brief Reference Texture Implementation.
24 *//*--------------------------------------------------------------------*/
25
26#include "tcuDefs.hpp"
27#include "tcuVector.hpp"
28#include "deArrayBuffer.hpp"
29
30#include <vector>
31#include <ostream>
32
33namespace tcu
34{
35
36/*--------------------------------------------------------------------*//*!
37 * \brief Texture format
38 *//*--------------------------------------------------------------------*/
39class TextureFormat
40{
41public:
42	enum ChannelOrder
43	{
44		R = 0,
45		A,
46		I,
47		L,
48		LA,
49		RG,
50		RA,
51		RGB,
52		RGBA,
53		ARGB,
54		BGRA,
55
56		sR,
57		sRG,
58		sRGB,
59		sRGBA,
60
61		D,
62		S,
63		DS,
64
65		CHANNELORDER_LAST
66	};
67
68	enum ChannelType
69	{
70		SNORM_INT8 = 0,
71		SNORM_INT16,
72		SNORM_INT32,
73		UNORM_INT8,
74		UNORM_INT16,
75		UNORM_INT24,
76		UNORM_INT32,
77		UNORM_SHORT_565,
78		UNORM_SHORT_555,
79		UNORM_SHORT_4444,
80		UNORM_SHORT_5551,
81		UNORM_INT_101010,
82		UNORM_INT_1010102_REV,
83		UNSIGNED_INT_1010102_REV,
84		UNSIGNED_INT_11F_11F_10F_REV,
85		UNSIGNED_INT_999_E5_REV,
86		UNSIGNED_INT_24_8,
87		SIGNED_INT8,
88		SIGNED_INT16,
89		SIGNED_INT32,
90		UNSIGNED_INT8,
91		UNSIGNED_INT16,
92		UNSIGNED_INT32,
93		HALF_FLOAT,
94		FLOAT,
95		FLOAT_UNSIGNED_INT_24_8_REV,
96
97		CHANNELTYPE_LAST
98	};
99
100	ChannelOrder	order;
101	ChannelType		type;
102
103	TextureFormat (ChannelOrder order_, ChannelType type_)
104		: order	(order_)
105		, type	(type_)
106	{
107	}
108
109	TextureFormat (void)
110		: order	(CHANNELORDER_LAST)
111		, type	(CHANNELTYPE_LAST)
112	{
113	}
114
115	int getPixelSize (void) const;
116
117	bool operator== (const TextureFormat& other) const { return !(*this != other); }
118	bool operator!= (const TextureFormat& other) const
119	{
120		return (order != other.order || type != other.type);
121	}
122} DE_WARN_UNUSED_TYPE;
123
124/*--------------------------------------------------------------------*//*!
125 * \brief Texture swizzle
126 *//*--------------------------------------------------------------------*/
127struct TextureSwizzle
128{
129	enum Channel
130	{
131		// \note CHANNEL_N must equal int N
132		CHANNEL_0 = 0,
133		CHANNEL_1,
134		CHANNEL_2,
135		CHANNEL_3,
136
137		CHANNEL_ZERO,
138		CHANNEL_ONE,
139
140		CHANNEL_LAST
141	};
142
143	Channel components[4];
144};
145
146//! get the swizzle used to expand texture data with a given channel order to RGBA form
147const TextureSwizzle& getChannelReadSwizzle		(TextureFormat::ChannelOrder order);
148
149//! get the swizzle used to narrow RGBA form data to native texture data with a given channel order
150const TextureSwizzle& getChannelWriteSwizzle	(TextureFormat::ChannelOrder order);
151
152/*--------------------------------------------------------------------*//*!
153 * \brief Sampling parameters
154 *//*--------------------------------------------------------------------*/
155class Sampler
156{
157public:
158	enum WrapMode
159	{
160		CLAMP_TO_EDGE = 0,	//! Clamp to edge
161		CLAMP_TO_BORDER,	//! Use border color at edge
162		REPEAT_GL,			//! Repeat with OpenGL semantics
163		REPEAT_CL,			//! Repeat with OpenCL semantics
164		MIRRORED_REPEAT_GL,	//! Mirrored repeat with OpenGL semantics
165		MIRRORED_REPEAT_CL, //! Mirrored repeat with OpenCL semantics
166
167		WRAPMODE_LAST
168	};
169
170	enum FilterMode
171	{
172		NEAREST = 0,
173		LINEAR,
174
175		NEAREST_MIPMAP_NEAREST,
176		NEAREST_MIPMAP_LINEAR,
177		LINEAR_MIPMAP_NEAREST,
178		LINEAR_MIPMAP_LINEAR,
179
180		FILTERMODE_LAST
181	};
182
183	enum CompareMode
184	{
185		COMPAREMODE_NONE = 0,
186		COMPAREMODE_LESS,
187		COMPAREMODE_LESS_OR_EQUAL,
188		COMPAREMODE_GREATER,
189		COMPAREMODE_GREATER_OR_EQUAL,
190		COMPAREMODE_EQUAL,
191		COMPAREMODE_NOT_EQUAL,
192		COMPAREMODE_ALWAYS,
193		COMPAREMODE_NEVER,
194
195		COMPAREMODE_LAST
196	};
197
198	// Wrap control
199	WrapMode		wrapS;
200	WrapMode		wrapT;
201	WrapMode		wrapR;
202
203	// Minifcation & magnification
204	FilterMode		minFilter;
205	FilterMode		magFilter;
206	float			lodThreshold;		// lod <= lodThreshold ? magnified : minified
207
208	// Coordinate normalization
209	bool			normalizedCoords;
210
211	// Shadow comparison
212	CompareMode		compare;
213	int				compareChannel;
214
215	// Border color
216	Vec4			borderColor;
217
218	// Seamless cube map filtering
219	bool			seamlessCubeMap;
220
221	Sampler (WrapMode		wrapS_,
222			 WrapMode		wrapT_,
223			 WrapMode		wrapR_,
224			 FilterMode		minFilter_,
225			 FilterMode		magFilter_,
226			 float			lodThreshold_		= 0.0f,
227			 bool			normalizedCoords_	= true,
228			 CompareMode	compare_			= COMPAREMODE_NONE,
229			 int			compareChannel_		= 0,
230			 const Vec4&	borderColor_		= Vec4(0.0f, 0.0f, 0.0f, 0.0f),
231			 bool			seamlessCubeMap_	= false)
232		: wrapS				(wrapS_)
233		, wrapT				(wrapT_)
234		, wrapR				(wrapR_)
235		, minFilter			(minFilter_)
236		, magFilter			(magFilter_)
237		, lodThreshold		(lodThreshold_)
238		, normalizedCoords	(normalizedCoords_)
239		, compare			(compare_)
240		, compareChannel	(compareChannel_)
241		, borderColor		(borderColor_)
242		, seamlessCubeMap	(seamlessCubeMap_)
243	{
244	}
245
246	Sampler (void)
247		: wrapS				(WRAPMODE_LAST)
248		, wrapT				(WRAPMODE_LAST)
249		, wrapR				(WRAPMODE_LAST)
250		, minFilter			(FILTERMODE_LAST)
251		, magFilter			(FILTERMODE_LAST)
252		, lodThreshold		(0.0f)
253		, normalizedCoords	(true)
254		, compare			(COMPAREMODE_NONE)
255		, compareChannel	(0)
256		, borderColor		(0.0f, 0.0f, 0.0f, 0.0f)
257		, seamlessCubeMap	(false)
258	{
259	}
260} DE_WARN_UNUSED_TYPE;
261
262// Calculate pitches for pixel data with no padding.
263IVec3 calculatePackedPitch (const TextureFormat& format, const IVec3& size);
264
265class TextureLevel;
266
267/*--------------------------------------------------------------------*//*!
268 * \brief Read-only pixel data access
269 *
270 * ConstPixelBufferAccess encapsulates pixel data pointer along with
271 * format and layout information. It can be used for read-only access
272 * to arbitrary pixel buffers.
273 *
274 * Access objects are like iterators or pointers. They can be passed around
275 * as values and are valid as long as the storage doesn't change.
276 *//*--------------------------------------------------------------------*/
277class ConstPixelBufferAccess
278{
279public:
280							ConstPixelBufferAccess		(void);
281							ConstPixelBufferAccess		(const TextureLevel& level);
282							ConstPixelBufferAccess		(const TextureFormat& format, int width, int height, int depth, const void* data);
283							ConstPixelBufferAccess		(const TextureFormat& format, const IVec3& size, const void* data);
284							ConstPixelBufferAccess		(const TextureFormat& format, int width, int height, int depth, int rowPitch, int slicePitch, const void* data);
285							ConstPixelBufferAccess		(const TextureFormat& format, const IVec3& size, const IVec3& pitch, const void* data);
286
287	const TextureFormat&	getFormat					(void) const	{ return m_format;					}
288	const IVec3&			getSize						(void) const	{ return m_size;					}
289	int						getWidth					(void) const	{ return m_size.x();				}
290	int						getHeight					(void) const	{ return m_size.y();				}
291	int						getDepth					(void) const	{ return m_size.z();				}
292	int						getPixelPitch				(void) const	{ return m_pitch.x();				}
293	int						getRowPitch					(void) const	{ return m_pitch.y();				}
294	int						getSlicePitch				(void) const	{ return m_pitch.z();				}
295	const IVec3&			getPitch					(void) const	{ return m_pitch;					}
296
297	const void*				getDataPtr					(void) const	{ return m_data;					}
298	int						getDataSize					(void) const	{ return m_size.z()*m_pitch.z();	}
299
300	const void*				getPixelPtr					(int x, int y, int z = 0) const { return (const deUint8*)m_data + x * m_pitch.x() + y * m_pitch.y() + z * m_pitch.z(); }
301
302	Vec4					getPixel					(int x, int y, int z = 0) const;
303	IVec4					getPixelInt					(int x, int y, int z = 0) const;
304	UVec4					getPixelUint				(int x, int y, int z = 0) const { return getPixelInt(x, y, z).cast<deUint32>(); }
305
306	template<typename T>
307	Vector<T, 4>			getPixelT					(int x, int y, int z = 0) const;
308
309	float					getPixDepth					(int x, int y, int z = 0) const;
310	int						getPixStencil				(int x, int y, int z = 0) const;
311
312	Vec4					sample1D					(const Sampler& sampler, Sampler::FilterMode filter, float s, int level) const;
313	Vec4					sample2D					(const Sampler& sampler, Sampler::FilterMode filter, float s, float t, int depth) const;
314	Vec4					sample3D					(const Sampler& sampler, Sampler::FilterMode filter, float s, float t, float r) const;
315
316	Vec4					sample1DOffset				(const Sampler& sampler, Sampler::FilterMode filter, float s, const IVec2& offset) const;
317	Vec4					sample2DOffset				(const Sampler& sampler, Sampler::FilterMode filter, float s, float t, const IVec3& offset) const;
318	Vec4					sample3DOffset				(const Sampler& sampler, Sampler::FilterMode filter, float s, float t, float r, const IVec3& offset) const;
319
320	float					sample1DCompare				(const Sampler& sampler, Sampler::FilterMode filter, float ref, float s, const IVec2& offset) const;
321	float					sample2DCompare				(const Sampler& sampler, Sampler::FilterMode filter, float ref, float s, float t, const IVec3& offset) const;
322
323protected:
324	TextureFormat			m_format;
325	IVec3					m_size;
326	IVec3					m_pitch;	//!< (pixelPitch, rowPitch, slicePitch)
327	mutable void*			m_data;
328} DE_WARN_UNUSED_TYPE;
329
330/*--------------------------------------------------------------------*//*!
331 * \brief Read-write pixel data access
332 *
333 * This class extends read-only access object by providing write functionality.
334 *
335 * \note PixelBufferAccess may not have any data members nor add any
336 *		 virtual functions. It must be possible to reinterpret_cast<>
337 *		 PixelBufferAccess to ConstPixelBufferAccess.
338 *//*--------------------------------------------------------------------*/
339class PixelBufferAccess : public ConstPixelBufferAccess
340{
341public:
342						PixelBufferAccess	(void) {}
343						PixelBufferAccess	(TextureLevel& level);
344						PixelBufferAccess	(const TextureFormat& format, int width, int height, int depth, void* data);
345						PixelBufferAccess	(const TextureFormat& format, const IVec3& size, void* data);
346						PixelBufferAccess	(const TextureFormat& format, int width, int height, int depth, int rowPitch, int slicePitch, void* data);
347						PixelBufferAccess	(const TextureFormat& format, const IVec3& size, const IVec3& pitch, void* data);
348
349	void*				getDataPtr			(void) const { return m_data; }
350	void*				getPixelPtr			(int x, int y, int z = 0) const { return (deUint8*)m_data + x * m_pitch.x() + y * m_pitch.y() + z * m_pitch.z(); }
351
352	void				setPixels			(const void* buf, int bufSize) const;
353	void				setPixel			(const tcu::Vec4& color, int x, int y, int z = 0) const;
354	void				setPixel			(const tcu::IVec4& color, int x, int y, int z = 0) const;
355	void				setPixel			(const tcu::UVec4& color, int x, int y, int z = 0) const { setPixel(color.cast<int>(), x, y, z); }
356
357	void				setPixDepth			(float depth, int x, int y, int z = 0) const;
358	void				setPixStencil		(int stencil, int x, int y, int z = 0) const;
359} DE_WARN_UNUSED_TYPE;
360
361/*--------------------------------------------------------------------*//*!
362 * \brief Generic pixel data container
363 *
364 * This container supports all valid TextureFormat combinations and
365 * both 2D and 3D textures. To read or manipulate data access object must
366 * be queried using getAccess().
367 *//*--------------------------------------------------------------------*/
368class TextureLevel
369{
370public:
371								TextureLevel		(void);
372								TextureLevel		(const TextureFormat& format);
373								TextureLevel		(const TextureFormat& format, int width, int height, int depth = 1);
374								~TextureLevel		(void);
375
376	const IVec3&				getSize				(void) const	{ return m_size;		}
377	int							getWidth			(void) const	{ return m_size.x();	}
378	int							getHeight			(void) const	{ return m_size.y();	}
379	int							getDepth			(void) const	{ return m_size.z();	}
380	bool						isEmpty				(void) const	{ return m_size.x() * m_size.y() * m_size.z() == 0; }
381	const TextureFormat			getFormat			(void) const	{ return m_format;	}
382
383	void						setStorage			(const TextureFormat& format, int width, int heigth, int depth = 1);
384	void						setSize				(int width, int height, int depth = 1);
385
386	PixelBufferAccess			getAccess			(void)			{ return PixelBufferAccess(m_format, m_size, calculatePackedPitch(m_format, m_size), getPtr());			}
387	ConstPixelBufferAccess		getAccess			(void) const	{ return ConstPixelBufferAccess(m_format, m_size, calculatePackedPitch(m_format, m_size), getPtr());	}
388
389private:
390	void*						getPtr				(void)			{ return m_data.getPtr(); }
391	const void*					getPtr				(void) const	{ return m_data.getPtr(); }
392
393	TextureFormat				m_format;
394	IVec3						m_size;
395	de::ArrayBuffer<deUint8>	m_data;
396
397	friend class ConstPixelBufferAccess;
398} DE_WARN_UNUSED_TYPE;
399
400Vec4	sampleLevelArray1D				(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, int level, float lod);
401Vec4	sampleLevelArray2D				(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, float t, int depth, float lod);
402Vec4	sampleLevelArray3D				(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, float t, float r, float lod);
403
404Vec4	sampleLevelArray1DOffset		(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, float lod, const IVec2& offset);
405Vec4	sampleLevelArray2DOffset		(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, float t, float lod, const IVec3& offset);
406Vec4	sampleLevelArray3DOffset		(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, float t, float r, float lod, const IVec3& offset);
407
408float	sampleLevelArray1DCompare		(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float ref, float s, float lod, const IVec2& offset);
409float	sampleLevelArray2DCompare		(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float ref, float s, float t, float lod, const IVec3& offset);
410
411Vec4	gatherArray2DOffsets			(const ConstPixelBufferAccess& src, const Sampler& sampler, float s, float t, int depth, int componentNdx, const IVec2 (&offsets)[4]);
412Vec4	gatherArray2DOffsetsCompare		(const ConstPixelBufferAccess& src, const Sampler& sampler, float ref, float s, float t, int depth, const IVec2 (&offsets)[4]);
413
414enum CubeFace
415{
416	CUBEFACE_NEGATIVE_X = 0,
417	CUBEFACE_POSITIVE_X,
418	CUBEFACE_NEGATIVE_Y,
419	CUBEFACE_POSITIVE_Y,
420	CUBEFACE_NEGATIVE_Z,
421	CUBEFACE_POSITIVE_Z,
422
423	CUBEFACE_LAST
424};
425
426/*--------------------------------------------------------------------*//*!
427 * \brief Coordinates projected onto cube face.
428 *//*--------------------------------------------------------------------*/
429template<typename T>
430struct CubeFaceCoords
431{
432	CubeFace		face;
433	T				s;
434	T				t;
435
436					CubeFaceCoords		(CubeFace face_, T s_, T t_) : face(face_), s(s_), t(t_) {}
437					CubeFaceCoords		(CubeFace face_, const Vector<T, 2>& c) : face(face_), s(c.x()), t(c.y()) {}
438} DE_WARN_UNUSED_TYPE;
439
440typedef CubeFaceCoords<float>	CubeFaceFloatCoords;
441typedef CubeFaceCoords<int>		CubeFaceIntCoords;
442
443CubeFace				selectCubeFace			(const Vec3& coords);
444Vec2					projectToFace			(CubeFace face, const Vec3& coords);
445CubeFaceFloatCoords		getCubeFaceCoords		(const Vec3& coords);
446CubeFaceIntCoords		remapCubeEdgeCoords		(const CubeFaceIntCoords& coords, int size);
447
448/*--------------------------------------------------------------------*//*!
449 * \brief 1D Texture View
450 *//*--------------------------------------------------------------------*/
451class Texture1DView
452{
453public:
454									Texture1DView		(int numLevels, const ConstPixelBufferAccess* levels);
455
456	int								getNumLevels		(void) const	{ return m_numLevels;										}
457	int								getWidth			(void) const	{ return m_numLevels > 0 ? m_levels[0].getWidth()	: 0;	}
458	const ConstPixelBufferAccess&	getLevel			(int ndx) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[ndx];	}
459	const ConstPixelBufferAccess*	getLevels			(void) const	{ return m_levels;											}
460
461	Vec4							sample				(const Sampler& sampler, float s, float lod) const;
462	Vec4							sampleOffset		(const Sampler& sampler, float s, float lod, deInt32 offset) const;
463	float							sampleCompare		(const Sampler& sampler, float ref, float s, float lod) const;
464	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float lod, deInt32 offset) const;
465
466protected:
467	int								m_numLevels;
468	const ConstPixelBufferAccess*	m_levels;
469} DE_WARN_UNUSED_TYPE;
470
471inline Texture1DView::Texture1DView (int numLevels, const ConstPixelBufferAccess* levels)
472	: m_numLevels	(numLevels)
473	, m_levels		(levels)
474{
475	DE_ASSERT(m_numLevels >= 0 && ((m_numLevels == 0) == !m_levels));
476}
477
478inline Vec4 Texture1DView::sample (const Sampler& sampler, float s, float lod) const
479{
480	return sampleLevelArray1D(m_levels, m_numLevels, sampler, s, 0 /* depth */, lod);
481}
482
483inline Vec4 Texture1DView::sampleOffset (const Sampler& sampler, float s, float lod, deInt32 offset) const
484{
485	return sampleLevelArray1DOffset(m_levels, m_numLevels, sampler, s, lod, IVec2(offset, 0));
486}
487
488inline float Texture1DView::sampleCompare (const Sampler& sampler, float ref, float s, float lod) const
489{
490	return sampleLevelArray1DCompare(m_levels, m_numLevels, sampler, ref, s, lod, IVec2(0, 0));
491}
492
493inline float Texture1DView::sampleCompareOffset (const Sampler& sampler, float ref, float s, float lod, deInt32 offset) const
494{
495	return sampleLevelArray1DCompare(m_levels, m_numLevels, sampler, ref, s, lod, IVec2(offset, 0));
496}
497
498/*--------------------------------------------------------------------*//*!
499 * \brief 2D Texture View
500 *//*--------------------------------------------------------------------*/
501class Texture2DView
502{
503public:
504									Texture2DView		(int numLevels, const ConstPixelBufferAccess* levels);
505
506	int								getNumLevels		(void) const	{ return m_numLevels;										}
507	int								getWidth			(void) const	{ return m_numLevels > 0 ? m_levels[0].getWidth()	: 0;	}
508	int								getHeight			(void) const	{ return m_numLevels > 0 ? m_levels[0].getHeight()	: 0;	}
509	const ConstPixelBufferAccess&	getLevel			(int ndx) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[ndx];	}
510	const ConstPixelBufferAccess*	getLevels			(void) const	{ return m_levels;											}
511
512	Vec4							sample				(const Sampler& sampler, float s, float t, float lod) const;
513	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float lod, const IVec2& offset) const;
514	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float lod) const;
515	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float lod, const IVec2& offset) const;
516
517	Vec4							gatherOffsets		(const Sampler& sampler, float s, float t, int componentNdx, const IVec2 (&offsets)[4]) const;
518	Vec4							gatherOffsetsCompare(const Sampler& sampler, float ref, float s, float t, const IVec2 (&offsets)[4]) const;
519
520protected:
521	int								m_numLevels;
522	const ConstPixelBufferAccess*	m_levels;
523} DE_WARN_UNUSED_TYPE;
524
525inline Texture2DView::Texture2DView (int numLevels, const ConstPixelBufferAccess* levels)
526	: m_numLevels	(numLevels)
527	, m_levels		(levels)
528{
529	DE_ASSERT(m_numLevels >= 0 && ((m_numLevels == 0) == !m_levels));
530}
531
532inline Vec4 Texture2DView::sample (const Sampler& sampler, float s, float t, float lod) const
533{
534	return sampleLevelArray2D(m_levels, m_numLevels, sampler, s, t, 0 /* depth */, lod);
535}
536
537inline Vec4 Texture2DView::sampleOffset (const Sampler& sampler, float s, float t, float lod, const IVec2& offset) const
538{
539	return sampleLevelArray2DOffset(m_levels, m_numLevels, sampler, s, t, lod, IVec3(offset.x(), offset.y(), 0));
540}
541
542inline float Texture2DView::sampleCompare (const Sampler& sampler, float ref, float s, float t, float lod) const
543{
544	return sampleLevelArray2DCompare(m_levels, m_numLevels, sampler, ref, s, t, lod, IVec3(0, 0, 0));
545}
546
547inline float Texture2DView::sampleCompareOffset (const Sampler& sampler, float ref, float s, float t, float lod, const IVec2& offset) const
548{
549	return sampleLevelArray2DCompare(m_levels, m_numLevels, sampler, ref, s, t, lod, IVec3(offset.x(), offset.y(), 0));
550}
551
552inline Vec4 Texture2DView::gatherOffsets (const Sampler& sampler, float s, float t, int componentNdx, const IVec2 (&offsets)[4]) const
553{
554	return gatherArray2DOffsets(m_levels[0], sampler, s, t, 0, componentNdx, offsets);
555}
556
557inline Vec4 Texture2DView::gatherOffsetsCompare (const Sampler& sampler, float ref, float s, float t, const IVec2 (&offsets)[4]) const
558{
559	return gatherArray2DOffsetsCompare(m_levels[0], sampler, ref, s, t, 0, offsets);
560}
561
562/*--------------------------------------------------------------------*//*!
563 * \brief Base class for textures that have single mip-map pyramid
564 *//*--------------------------------------------------------------------*/
565class TextureLevelPyramid
566{
567public:
568									TextureLevelPyramid	(const TextureFormat& format, int numLevels);
569									TextureLevelPyramid	(const TextureLevelPyramid& other);
570									~TextureLevelPyramid(void);
571
572	const TextureFormat&			getFormat			(void) const			{ return m_format;					}
573	bool							isLevelEmpty		(int levelNdx) const	{ return m_data[levelNdx].empty();	}
574
575	int								getNumLevels		(void) const			{ return (int)m_access.size();		}
576	const ConstPixelBufferAccess&	getLevel			(int ndx) const			{ return m_access[ndx];				}
577	const PixelBufferAccess&		getLevel			(int ndx)				{ return m_access[ndx];				}
578
579	const ConstPixelBufferAccess*	getLevels			(void) const			{ return &m_access[0];				}
580	const PixelBufferAccess*		getLevels			(void)					{ return &m_access[0];				}
581
582	void							allocLevel			(int levelNdx, int width, int height, int depth);
583	void							clearLevel			(int levelNdx);
584
585	TextureLevelPyramid&			operator=			(const TextureLevelPyramid& other);
586
587private:
588	typedef de::ArrayBuffer<deUint8> LevelData;
589
590	TextureFormat					m_format;
591	std::vector<LevelData>			m_data;
592	std::vector<PixelBufferAccess>	m_access;
593} DE_WARN_UNUSED_TYPE;
594
595/*--------------------------------------------------------------------*//*!
596 * \brief 1D Texture reference implementation
597 *//*--------------------------------------------------------------------*/
598class Texture1D : private TextureLevelPyramid
599{
600public:
601									Texture1D			(const TextureFormat& format, int width);
602									Texture1D			(const Texture1D& other);
603									~Texture1D			(void);
604
605	int								getWidth			(void) const	{ return m_width;	}
606	const Texture1DView&			getView				(void) const	{ return m_view;	}
607
608	void							allocLevel			(int levelNdx);
609
610	// Sampling
611	Vec4							sample				(const Sampler& sampler, float s, float lod) const;
612	Vec4							sampleOffset		(const Sampler& sampler, float s, float lod, deInt32 offset) const;
613
614	using TextureLevelPyramid::getFormat;
615	using TextureLevelPyramid::getNumLevels;
616	using TextureLevelPyramid::getLevel;
617	using TextureLevelPyramid::clearLevel;
618	using TextureLevelPyramid::isLevelEmpty;
619
620	Texture1D&						operator=			(const Texture1D& other);
621
622	operator Texture1DView (void) const { return m_view; }
623
624private:
625	int								m_width;
626	Texture1DView					m_view;
627} DE_WARN_UNUSED_TYPE;
628
629inline Vec4 Texture1D::sample (const Sampler& sampler, float s, float lod) const
630{
631	return m_view.sample(sampler, s, lod);
632}
633
634inline Vec4 Texture1D::sampleOffset (const Sampler& sampler, float s, float lod, deInt32 offset) const
635{
636	return m_view.sampleOffset(sampler, s, lod, offset);
637}
638
639/*--------------------------------------------------------------------*//*!
640 * \brief 2D Texture reference implementation
641 *//*--------------------------------------------------------------------*/
642class Texture2D : private TextureLevelPyramid
643{
644public:
645									Texture2D			(const TextureFormat& format, int width, int height);
646									Texture2D			(const Texture2D& other);
647									~Texture2D			(void);
648
649	int								getWidth			(void) const	{ return m_width;	}
650	int								getHeight			(void) const	{ return m_height;	}
651	const Texture2DView&			getView				(void) const	{ return m_view;	}
652
653	void							allocLevel			(int levelNdx);
654
655	// Sampling
656	Vec4							sample				(const Sampler& sampler, float s, float t, float lod) const;
657	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float lod, const IVec2& offset) const;
658	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float lod) const;
659	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float lod, const IVec2& offset) const;
660
661	Vec4							gatherOffsets		(const Sampler& sampler, float s, float t, int componentNdx, const IVec2 (&offsets)[4]) const;
662	Vec4							gatherOffsetsCompare(const Sampler& sampler, float ref, float s, float t, const IVec2 (&offsets)[4]) const;
663
664	using TextureLevelPyramid::getFormat;
665	using TextureLevelPyramid::getNumLevels;
666	using TextureLevelPyramid::getLevel;
667	using TextureLevelPyramid::clearLevel;
668	using TextureLevelPyramid::isLevelEmpty;
669
670	Texture2D&						operator=			(const Texture2D& other);
671
672	operator Texture2DView (void) const { return m_view; }
673
674private:
675	int								m_width;
676	int								m_height;
677	Texture2DView					m_view;
678} DE_WARN_UNUSED_TYPE;
679
680inline Vec4 Texture2D::sample (const Sampler& sampler, float s, float t, float lod) const
681{
682	return m_view.sample(sampler, s, t, lod);
683}
684
685inline Vec4 Texture2D::sampleOffset (const Sampler& sampler, float s, float t, float lod, const IVec2& offset) const
686{
687	return m_view.sampleOffset(sampler, s, t, lod, offset);
688}
689
690inline float Texture2D::sampleCompare (const Sampler& sampler, float ref, float s, float t, float lod) const
691{
692	return m_view.sampleCompare(sampler, ref, s, t, lod);
693}
694
695inline float Texture2D::sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float lod, const IVec2& offset) const
696{
697	return m_view.sampleCompareOffset(sampler, ref, s, t, lod, offset);
698}
699
700inline Vec4 Texture2D::gatherOffsets (const Sampler& sampler, float s, float t, int componentNdx, const IVec2 (&offsets)[4]) const
701{
702	return m_view.gatherOffsets(sampler, s, t, componentNdx, offsets);
703}
704
705inline Vec4 Texture2D::gatherOffsetsCompare (const Sampler& sampler, float ref, float s, float t, const IVec2 (&offsets)[4]) const
706{
707	return m_view.gatherOffsetsCompare(sampler, ref, s, t, offsets);
708}
709
710/*--------------------------------------------------------------------*//*!
711 * \brief Cube Map Texture View
712 *//*--------------------------------------------------------------------*/
713class TextureCubeView
714{
715public:
716									TextureCubeView		(void);
717									TextureCubeView		(int numLevels, const ConstPixelBufferAccess* const (&levels)[CUBEFACE_LAST]);
718
719	int								getNumLevels		(void) const	{ return m_numLevels;										}
720	int								getSize				(void) const	{ return m_numLevels > 0 ? m_levels[0][0].getWidth() : 0;	}
721	const ConstPixelBufferAccess&	getLevelFace		(int ndx, CubeFace face) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[face][ndx];	}
722	const ConstPixelBufferAccess*	getFaceLevels		(CubeFace face) const			{ return m_levels[face];					}
723
724	Vec4							sample				(const Sampler& sampler, float s, float t, float p, float lod) const;
725	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float r, float lod) const;
726
727	Vec4							gather				(const Sampler& sampler, float s, float t, float r, int componentNdx) const;
728	Vec4							gatherCompare		(const Sampler& sampler, float ref, float s, float t, float r) const;
729
730protected:
731	int								m_numLevels;
732	const ConstPixelBufferAccess*	m_levels[CUBEFACE_LAST];
733} DE_WARN_UNUSED_TYPE;
734
735/*--------------------------------------------------------------------*//*!
736 * \brief Cube Map Texture reference implementation
737 *//*--------------------------------------------------------------------*/
738class TextureCube
739{
740public:
741									TextureCube			(const TextureFormat& format, int size);
742									TextureCube			(const TextureCube& other);
743									~TextureCube		(void);
744
745	const TextureFormat&			getFormat			(void) const	{ return m_format;	}
746	int								getSize				(void) const	{ return m_size;	}
747
748	int								getNumLevels		(void) const					{ return (int)m_access[0].size();	}
749	const ConstPixelBufferAccess&	getLevelFace		(int ndx, CubeFace face) const	{ return m_access[face][ndx];		}
750	const PixelBufferAccess&		getLevelFace		(int ndx, CubeFace face)		{ return m_access[face][ndx];		}
751
752	void							allocLevel			(CubeFace face, int levelNdx);
753	void							clearLevel			(CubeFace face, int levelNdx);
754	bool							isLevelEmpty		(CubeFace face, int levelNdx) const		{ return m_data[face][levelNdx].empty();	}
755
756	Vec4							sample				(const Sampler& sampler, float s, float t, float p, float lod) const;
757	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float r, float lod) const;
758
759	Vec4							gather				(const Sampler& sampler, float s, float t, float r, int componentNdx) const;
760	Vec4							gatherCompare		(const Sampler& sampler, float ref, float s, float t, float r) const;
761
762	TextureCube&					operator=			(const TextureCube& other);
763
764	operator TextureCubeView (void) const { return m_view; }
765
766private:
767	typedef de::ArrayBuffer<deUint8> LevelData;
768
769	TextureFormat					m_format;
770	int								m_size;
771	std::vector<LevelData>			m_data[CUBEFACE_LAST];
772	std::vector<PixelBufferAccess>	m_access[CUBEFACE_LAST];
773	TextureCubeView					m_view;
774} DE_WARN_UNUSED_TYPE;
775
776inline Vec4 TextureCube::sample (const Sampler& sampler, float s, float t, float p, float lod) const
777{
778	return m_view.sample(sampler, s, t, p, lod);
779}
780
781inline float TextureCube::sampleCompare (const Sampler& sampler, float ref, float s, float t, float r, float lod) const
782{
783	return m_view.sampleCompare(sampler, ref, s, t, r, lod);
784}
785
786inline Vec4 TextureCube::gather (const Sampler& sampler, float s, float t, float r, int componentNdx) const
787{
788	return m_view.gather(sampler, s, t, r, componentNdx);
789}
790
791inline Vec4 TextureCube::gatherCompare (const Sampler& sampler, float ref, float s, float t, float r) const
792{
793	return m_view.gatherCompare(sampler, ref, s, t, r);
794}
795
796/*--------------------------------------------------------------------*//*!
797 * \brief 1D Array Texture View
798 *//*--------------------------------------------------------------------*/
799class Texture1DArrayView
800{
801public:
802									Texture1DArrayView	(int numLevels, const ConstPixelBufferAccess* levels);
803
804	int								getWidth			(void) const	{ return m_numLevels > 0 ? m_levels[0].getWidth()	: 0;	}
805	int								getNumLayers		(void) const	{ return m_numLevels > 0 ? m_levels[0].getHeight()	: 0;	}
806	int								getNumLevels		(void) const	{ return m_numLevels;										}
807	const ConstPixelBufferAccess&	getLevel			(int ndx) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[ndx];	}
808	const ConstPixelBufferAccess*	getLevels			(void) const	{ return m_levels;											}
809
810	Vec4							sample				(const Sampler& sampler, float s, float t, float lod) const;
811	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float lod, deInt32 offset) const;
812	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float lod) const;
813	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float lod, deInt32 offset) const;
814
815protected:
816	int								selectLayer			(float r) const;
817
818	int								m_numLevels;
819	const ConstPixelBufferAccess*	m_levels;
820} DE_WARN_UNUSED_TYPE;
821
822/*--------------------------------------------------------------------*//*!
823 * \brief 2D Array Texture View
824 *//*--------------------------------------------------------------------*/
825class Texture2DArrayView
826{
827public:
828									Texture2DArrayView	(int numLevels, const ConstPixelBufferAccess* levels);
829
830	int								getWidth			(void) const	{ return m_numLevels > 0 ? m_levels[0].getWidth()	: 0;	}
831	int								getHeight			(void) const	{ return m_numLevels > 0 ? m_levels[0].getHeight()	: 0;	}
832	int								getNumLayers		(void) const	{ return m_numLevels > 0 ? m_levels[0].getDepth()	: 0;	}
833	int								getNumLevels		(void) const	{ return m_numLevels;										}
834	const ConstPixelBufferAccess&	getLevel			(int ndx) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[ndx];	}
835	const ConstPixelBufferAccess*	getLevels			(void) const	{ return m_levels;											}
836
837	Vec4							sample				(const Sampler& sampler, float s, float t, float r, float lod) const;
838	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float r, float lod, const IVec2& offset) const;
839	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float r, float lod) const;
840	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float r, float lod, const IVec2& offset) const;
841
842	Vec4							gatherOffsets		(const Sampler& sampler, float s, float t, float r, int componentNdx, const IVec2 (&offsets)[4]) const;
843	Vec4							gatherOffsetsCompare(const Sampler& sampler, float ref, float s, float t, float r, const IVec2 (&offsets)[4]) const;
844
845protected:
846	int								selectLayer			(float r) const;
847
848	int								m_numLevels;
849	const ConstPixelBufferAccess*	m_levels;
850} DE_WARN_UNUSED_TYPE;
851
852/*--------------------------------------------------------------------*//*!
853 * \brief 1D Array Texture reference implementation
854 *//*--------------------------------------------------------------------*/
855class Texture1DArray : private TextureLevelPyramid
856{
857public:
858									Texture1DArray		(const TextureFormat& format, int width, int numLayers);
859									Texture1DArray		(const Texture1DArray& other);
860									~Texture1DArray		(void);
861
862	int								getWidth			(void) const	{ return m_width;		}
863	int								getNumLayers		(void) const	{ return m_numLayers;	}
864
865	void							allocLevel			(int levelNdx);
866
867	using TextureLevelPyramid::getFormat;
868	using TextureLevelPyramid::getNumLevels;
869	using TextureLevelPyramid::getLevel;
870	using TextureLevelPyramid::clearLevel;
871	using TextureLevelPyramid::isLevelEmpty;
872
873	Vec4							sample				(const Sampler& sampler, float s, float t, float lod) const;
874	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float lod, deInt32 offset) const;
875	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float lod) const;
876	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float lod, deInt32 offset) const;
877
878	Texture1DArray&					operator=			(const Texture1DArray& other);
879
880	operator Texture1DArrayView (void) const { return m_view; }
881
882private:
883	int								m_width;
884	int								m_numLayers;
885	Texture1DArrayView				m_view;
886} DE_WARN_UNUSED_TYPE;
887
888inline Vec4 Texture1DArray::sample (const Sampler& sampler, float s, float t, float lod) const
889{
890	return m_view.sample(sampler, s, t, lod);
891}
892
893inline Vec4 Texture1DArray::sampleOffset (const Sampler& sampler, float s, float t, float lod, deInt32 offset) const
894{
895	return m_view.sampleOffset(sampler, s, t, lod, offset);
896}
897
898inline float Texture1DArray::sampleCompare (const Sampler& sampler, float ref, float s, float t, float lod) const
899{
900	return m_view.sampleCompare(sampler, ref, s, t, lod);
901}
902
903inline float Texture1DArray::sampleCompareOffset (const Sampler& sampler, float ref, float s, float t, float lod, deInt32 offset) const
904{
905	return m_view.sampleCompareOffset(sampler, ref, s, t, lod, offset);
906}
907
908/*--------------------------------------------------------------------*//*!
909 * \brief 2D Array Texture reference implementation
910 *//*--------------------------------------------------------------------*/
911class Texture2DArray : private TextureLevelPyramid
912{
913public:
914									Texture2DArray		(const TextureFormat& format, int width, int height, int numLayers);
915									Texture2DArray		(const Texture2DArray& other);
916									~Texture2DArray		(void);
917
918	int								getWidth			(void) const	{ return m_width;		}
919	int								getHeight			(void) const	{ return m_height;		}
920	int								getNumLayers		(void) const	{ return m_numLayers;	}
921
922	void							allocLevel			(int levelNdx);
923
924	using TextureLevelPyramid::getFormat;
925	using TextureLevelPyramid::getNumLevels;
926	using TextureLevelPyramid::getLevel;
927	using TextureLevelPyramid::clearLevel;
928	using TextureLevelPyramid::isLevelEmpty;
929
930	Vec4							sample				(const Sampler& sampler, float s, float t, float r, float lod) const;
931	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float r, float lod, const IVec2& offset) const;
932	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float r, float lod) const;
933	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float r, float lod, const IVec2& offset) const;
934
935	Vec4							gatherOffsets		(const Sampler& sampler, float s, float t, float r, int componentNdx, const IVec2 (&offsets)[4]) const;
936	Vec4							gatherOffsetsCompare(const Sampler& sampler, float ref, float s, float t, float r, const IVec2 (&offsets)[4]) const;
937
938	Texture2DArray&					operator=			(const Texture2DArray& other);
939
940	operator Texture2DArrayView (void) const { return m_view; }
941
942private:
943	int								m_width;
944	int								m_height;
945	int								m_numLayers;
946	Texture2DArrayView				m_view;
947} DE_WARN_UNUSED_TYPE;
948
949inline Vec4 Texture2DArray::sample (const Sampler& sampler, float s, float t, float r, float lod) const
950{
951	return m_view.sample(sampler, s, t, r, lod);
952}
953
954inline Vec4 Texture2DArray::sampleOffset (const Sampler& sampler, float s, float t, float r, float lod, const IVec2& offset) const
955{
956	return m_view.sampleOffset(sampler, s, t, r, lod, offset);
957}
958
959inline float Texture2DArray::sampleCompare (const Sampler& sampler, float ref, float s, float t, float r, float lod) const
960{
961	return m_view.sampleCompare(sampler, ref, s, t, r, lod);
962}
963
964inline float Texture2DArray::sampleCompareOffset (const Sampler& sampler, float ref, float s, float t, float r, float lod, const IVec2& offset) const
965{
966	return m_view.sampleCompareOffset(sampler, ref, s, t, r, lod, offset);
967}
968
969inline Vec4 Texture2DArray::gatherOffsets (const Sampler& sampler, float s, float t, float r, int componentNdx, const IVec2 (&offsets)[4]) const
970{
971	return m_view.gatherOffsets(sampler, s, t, r, componentNdx, offsets);
972}
973
974inline Vec4 Texture2DArray::gatherOffsetsCompare (const Sampler& sampler, float ref, float s, float t, float r, const IVec2 (&offsets)[4]) const
975{
976	return m_view.gatherOffsetsCompare(sampler, ref, s, t, r, offsets);
977}
978
979/*--------------------------------------------------------------------*//*!
980 * \brief 3D Texture View
981 *//*--------------------------------------------------------------------*/
982class Texture3DView
983{
984public:
985									Texture3DView		(int numLevels, const ConstPixelBufferAccess* levels);
986
987	int								getWidth			(void) const	{ return m_numLevels > 0 ? m_levels[0].getWidth()	: 0;	}
988	int								getHeight			(void) const	{ return m_numLevels > 0 ? m_levels[0].getHeight()	: 0;	}
989	int								getDepth			(void) const	{ return m_numLevels > 0 ? m_levels[0].getDepth()	: 0;	}
990	int								getNumLevels		(void) const	{ return m_numLevels;										}
991	const ConstPixelBufferAccess&	getLevel			(int ndx) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[ndx];	}
992	const ConstPixelBufferAccess*	getLevels			(void) const	{ return m_levels;											}
993
994	Vec4							sample				(const Sampler& sampler, float s, float t, float r, float lod) const;
995	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float r, float lod, const IVec3& offset) const;
996
997protected:
998	int								m_numLevels;
999	const ConstPixelBufferAccess*	m_levels;
1000} DE_WARN_UNUSED_TYPE;
1001
1002inline Vec4 Texture3DView::sample (const Sampler& sampler, float s, float t, float r, float lod) const
1003{
1004	return sampleLevelArray3D(m_levels, m_numLevels, sampler, s, t, r, lod);
1005}
1006
1007inline Vec4 Texture3DView::sampleOffset (const Sampler& sampler, float s, float t, float r, float lod, const IVec3& offset) const
1008{
1009	return sampleLevelArray3DOffset(m_levels, m_numLevels, sampler, s, t, r, lod, offset);
1010}
1011
1012/*--------------------------------------------------------------------*//*!
1013 * \brief 3D Texture reference implementation
1014 *//*--------------------------------------------------------------------*/
1015class Texture3D : private TextureLevelPyramid
1016{
1017public:
1018									Texture3D			(const TextureFormat& format, int width, int height, int depth);
1019									Texture3D			(const Texture3D& other);
1020									~Texture3D			(void);
1021
1022	int								getWidth			(void) const	{ return m_width;	}
1023	int								getHeight			(void) const	{ return m_height;	}
1024	int								getDepth			(void) const	{ return m_depth;	}
1025
1026	void							allocLevel			(int levelNdx);
1027
1028	using TextureLevelPyramid::getFormat;
1029	using TextureLevelPyramid::getNumLevels;
1030	using TextureLevelPyramid::getLevel;
1031	using TextureLevelPyramid::clearLevel;
1032	using TextureLevelPyramid::isLevelEmpty;
1033
1034	Vec4							sample				(const Sampler& sampler, float s, float t, float r, float lod) const;
1035	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float r, float lod, const IVec3& offset) const;
1036
1037	Texture3D&						operator=			(const Texture3D& other);
1038
1039	operator Texture3DView (void) const { return m_view; }
1040
1041private:
1042	int								m_width;
1043	int								m_height;
1044	int								m_depth;
1045	Texture3DView					m_view;
1046} DE_WARN_UNUSED_TYPE;
1047
1048inline Vec4 Texture3D::sample (const Sampler& sampler, float s, float t, float r, float lod) const
1049{
1050	return m_view.sample(sampler, s, t, r, lod);
1051}
1052
1053inline Vec4 Texture3D::sampleOffset (const Sampler& sampler, float s, float t, float r, float lod, const IVec3& offset) const
1054{
1055	return m_view.sampleOffset(sampler, s, t, r, lod, offset);
1056}
1057
1058/*--------------------------------------------------------------------*//*!
1059 * \brief Cube Map Array Texture View
1060 *//*--------------------------------------------------------------------*/
1061class TextureCubeArrayView
1062{
1063public:
1064									TextureCubeArrayView	(int numLevels, const ConstPixelBufferAccess* levels);
1065
1066	int								getSize					(void) const	{ return m_numLevels > 0 ? m_levels[0].getWidth()	: 0;	}
1067	int								getDepth				(void) const	{ return m_numLevels > 0 ? m_levels[0].getDepth()	: 0;	}
1068	int								getNumLayers			(void) const	{ return getDepth()	/ 6;	}
1069	int								getNumLevels			(void) const	{ return m_numLevels;										}
1070	const ConstPixelBufferAccess&	getLevel				(int ndx) const	{ DE_ASSERT(de::inBounds(ndx, 0, m_numLevels)); return m_levels[ndx];	}
1071	const ConstPixelBufferAccess*	getLevels				(void) const	{ return m_levels;											}
1072
1073	Vec4							sample					(const Sampler& sampler, float s, float t, float r, float q, float lod) const;
1074	Vec4							sampleOffset			(const Sampler& sampler, float s, float t, float r, float q, float lod, const IVec2& offset) const;
1075	float							sampleCompare			(const Sampler& sampler, float ref, float s, float t, float r, float q, float lod) const;
1076	float							sampleCompareOffset		(const Sampler& sampler, float ref, float s, float t, float r, float q, float lod, const IVec2& offset) const;
1077
1078protected:
1079	int								selectLayer				(float q) const;
1080
1081	int								m_numLevels;
1082	const ConstPixelBufferAccess*	m_levels;
1083} DE_WARN_UNUSED_TYPE;
1084
1085/*--------------------------------------------------------------------*//*!
1086 * \brief Cube Map Array Texture reference implementation
1087 *//*--------------------------------------------------------------------*/
1088class TextureCubeArray : private TextureLevelPyramid
1089{
1090public:
1091									TextureCubeArray	(const TextureFormat& format, int size, int depth);
1092									TextureCubeArray	(const TextureCubeArray& other);
1093									~TextureCubeArray	(void);
1094
1095	int								getSize				(void) const	{ return m_size;	}
1096	int								getDepth			(void) const	{ return m_depth;	}
1097
1098	void							allocLevel			(int levelNdx);
1099
1100	using TextureLevelPyramid::getFormat;
1101	using TextureLevelPyramid::getNumLevels;
1102	using TextureLevelPyramid::getLevel;
1103	using TextureLevelPyramid::clearLevel;
1104	using TextureLevelPyramid::isLevelEmpty;
1105
1106	Vec4							sample				(const Sampler& sampler, float s, float t, float r, float q, float lod) const;
1107	Vec4							sampleOffset		(const Sampler& sampler, float s, float t, float r, float q, float lod, const IVec2& offset) const;
1108	float							sampleCompare		(const Sampler& sampler, float ref, float s, float t, float r, float q, float lod) const;
1109	float							sampleCompareOffset	(const Sampler& sampler, float ref, float s, float t, float r, float q, float lod, const IVec2& offset) const;
1110
1111	TextureCubeArray&				operator=			(const TextureCubeArray& other);
1112
1113	operator TextureCubeArrayView (void) const { return m_view; }
1114
1115private:
1116	int								m_size;
1117	int								m_depth;
1118	TextureCubeArrayView			m_view;
1119} DE_WARN_UNUSED_TYPE;
1120
1121inline Vec4 TextureCubeArray::sample (const Sampler& sampler, float s, float t, float r, float q, float lod) const
1122{
1123	return m_view.sample(sampler, s, t, r, q, lod);
1124}
1125
1126inline Vec4 TextureCubeArray::sampleOffset (const Sampler& sampler, float s, float t, float r, float q, float lod, const IVec2& offset) const
1127{
1128	return m_view.sampleOffset(sampler, s, t, r, q, lod, offset);
1129}
1130
1131inline float TextureCubeArray::sampleCompare (const Sampler& sampler, float ref, float s, float t, float r, float q, float lod) const
1132{
1133	return m_view.sampleCompare(sampler, ref, s, t, r, q, lod);
1134}
1135
1136inline float TextureCubeArray::sampleCompareOffset (const Sampler& sampler, float ref, float s, float t, float r, float q, float lod, const IVec2& offset) const
1137{
1138	return m_view.sampleCompareOffset(sampler, ref, s, t, r, q, lod, offset);
1139}
1140
1141// Stream operators.
1142std::ostream&		operator<<		(std::ostream& str, TextureFormat::ChannelOrder order);
1143std::ostream&		operator<<		(std::ostream& str, TextureFormat::ChannelType type);
1144std::ostream&		operator<<		(std::ostream& str, TextureFormat format);
1145std::ostream&		operator<<		(std::ostream& str, CubeFace face);
1146std::ostream&		operator<<		(std::ostream& str, const ConstPixelBufferAccess& access);
1147
1148} // tcu
1149
1150#endif // _TCUTEXTURE_HPP
1151