(Automated Tests) Added more coverage to Builder
[platform/core/uifw/dali-toolkit.git] / dali-toolkit / internal / controls / model3d-view / model3d-view-impl.cpp
1 /*
2  * Copyright (c) 2016 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 // CLASS HEADER
19 #include "model3d-view-impl.h"
20
21 // EXTERNAL INCLUDES
22 #include <dali/public-api/object/type-registry.h>
23 #include <dali/public-api/animation/constraint.h>
24 #include <dali/public-api/animation/constraint-source.h>
25 #include <dali/public-api/animation/constraints.h>
26 #include <dali/public-api/object/type-registry-helper.h>
27 #include <dali-toolkit/public-api/controls/model3d-view/model3d-view.h>
28 #include <dali/public-api/images/resource-image.h>
29 #include <dali/devel-api/adaptor-framework/file-loader.h>
30 #include <dali/devel-api/adaptor-framework/bitmap-loader.h>
31
32 // INTERNAL INCLUDES
33 #include <dali-toolkit/internal/controls/model3d-view/obj-loader.h>
34
35 namespace Dali
36 {
37
38 namespace Toolkit
39 {
40
41 namespace Internal
42 {
43
44 namespace
45 {
46
47 // Texture indices are constants.
48 enum TextureIndex
49 {
50   DIFFUSE_TEXTURE_INDEX,
51   NORMAL_TEXTURE_INDEX,
52   GLOSS_TEXTURE_INDEX
53 };
54
55 /**
56  * @brief Loads a texture from a file.
57  * @param[in] imageUrl The URL of the file
58  * @return A texture if loading succeeds, an empty handle otherwise
59  */
60 Texture LoadTexture( const char* imageUrl )
61 {
62   Texture texture;
63   Dali::BitmapLoader loader = Dali::BitmapLoader::New( imageUrl );
64   loader.Load();
65   PixelData pixelData = loader.GetPixelData();
66   if( pixelData )
67   {
68     texture = Texture::New( TextureType::TEXTURE_2D, pixelData.GetPixelFormat(), pixelData.GetWidth(), pixelData.GetHeight() );
69     texture.Upload( pixelData );
70     texture.GenerateMipmaps();
71   }
72
73   return texture;
74 }
75
76 // Type registration
77 BaseHandle Create()
78 {
79   return Toolkit::Model3dView::New();
80 }
81
82 // Setup properties, signals and actions using the type-registry.
83 DALI_TYPE_REGISTRATION_BEGIN( Toolkit::Model3dView, Toolkit::Control, Create );
84
85 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "geometryUrl",  STRING, GEOMETRY_URL)
86 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "materialUrl",  STRING, MATERIAL_URL)
87 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "imagesUrl",  STRING, IMAGES_URL)
88 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "illuminationType",  INTEGER, ILLUMINATION_TYPE)
89 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "texture0Url",  STRING, TEXTURE0_URL)
90 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "texture1Url",  STRING, TEXTURE1_URL)
91 DALI_PROPERTY_REGISTRATION( Toolkit, Model3dView, "texture2Url",  STRING, TEXTURE2_URL)
92
93 DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, Model3dView, "lightPosition",  VECTOR3, LIGHT_POSITION)
94
95 DALI_TYPE_REGISTRATION_END()
96
97
98 #define MAKE_SHADER(A)#A
99
100 //  Diffuse illumination shader
101
102 const char* SIMPLE_VERTEX_SHADER = MAKE_SHADER(
103   attribute highp vec3 aPosition;\n
104   attribute highp vec2 aTexCoord;\n
105   attribute highp vec3 aNormal;\n
106   varying mediump vec3 vIllumination;\n
107   uniform mediump vec3 uSize;\n
108   uniform mediump mat4 uMvpMatrix;\n
109   uniform mediump mat4 uModelView;\n
110   uniform mediump mat3 uNormalMatrix;
111   uniform mediump mat4 uObjectMatrix;\n
112   uniform mediump vec3 uLightPosition;\n
113
114   void main()\n
115   {\n
116     vec4 vertexPosition = vec4(aPosition*min(uSize.x, uSize.y), 1.0);\n
117     vertexPosition = uObjectMatrix * vertexPosition;\n
118     vertexPosition = uMvpMatrix * vertexPosition;\n
119
120     //Illumination in Model-View space - Transform attributes and uniforms\n
121     vec4 vertPos = uModelView * vec4(aPosition.xyz, 1.0);\n
122     vec3 normal = uNormalMatrix * aNormal;\n
123     vec4 lightPos = uModelView * vec4(uLightPosition, 1.0);\n
124     vec3 vecToLight = normalize( lightPos.xyz - vertPos.xyz );\n
125
126     float lightDiffuse = max( dot( vecToLight, normal ), 0.0 );\n
127     vIllumination = vec3(lightDiffuse * 0.5 + 0.5);\n
128
129     gl_Position = vertexPosition;\n
130   }\n
131 );
132
133 const char* SIMPLE_FRAGMENT_SHADER = MAKE_SHADER(
134   precision mediump float;\n
135   varying mediump vec3 vIllumination;\n
136   uniform lowp vec4 uColor;\n
137
138   void main()\n
139   {\n
140     gl_FragColor = vec4( vIllumination.rgb * uColor.rgb, uColor.a);\n
141   }\n
142 );
143
144 //  Diffuse and specular illumination shader with albedo texture
145
146 const char* VERTEX_SHADER = MAKE_SHADER(
147   attribute highp vec3 aPosition;\n
148   attribute highp vec2 aTexCoord;\n
149   attribute highp vec3 aNormal;\n
150   varying mediump vec2 vTexCoord;\n
151   varying mediump vec3 vIllumination;\n
152   varying mediump float vSpecular;\n
153   uniform mediump vec3 uSize;\n
154   uniform mediump mat4 uMvpMatrix;\n
155   uniform mediump mat4 uModelView;
156   uniform mediump mat3 uNormalMatrix;
157   uniform mediump mat4 uObjectMatrix;\n
158   uniform mediump vec3 uLightPosition;\n
159
160   void main()
161   {\n
162     vec4 vertexPosition = vec4(aPosition*min(uSize.x, uSize.y), 1.0);\n
163     vertexPosition = uObjectMatrix * vertexPosition;\n
164     vertexPosition = uMvpMatrix * vertexPosition;\n
165
166     //Illumination in Model-View space - Transform attributes and uniforms\n
167     vec4 vertPos = uModelView * vec4(aPosition.xyz, 1.0);\n
168     vec4 lightPos = uModelView * vec4(uLightPosition, 1.0);\n
169     vec3 normal = normalize(uNormalMatrix * aNormal);\n
170
171     vec3 vecToLight = normalize( lightPos.xyz - vertPos.xyz );\n
172     vec3 viewDir = normalize(-vertPos.xyz);
173
174     vec3 halfVector = normalize(viewDir + vecToLight);
175
176     float lightDiffuse = dot( vecToLight, normal );\n
177     lightDiffuse = max(0.0,lightDiffuse);\n
178     vIllumination = vec3(lightDiffuse * 0.5 + 0.5);\n
179
180     vec3 reflectDir = reflect(-vecToLight, normal);
181     vSpecular = pow( max(dot(reflectDir, viewDir), 0.0), 4.0 );
182
183     vTexCoord = aTexCoord;\n
184     gl_Position = vertexPosition;\n
185   }\n
186 );
187
188 const char* FRAGMENT_SHADER = MAKE_SHADER(
189   precision mediump float;\n
190   varying mediump vec2 vTexCoord;\n
191   varying mediump vec3 vIllumination;\n
192   varying mediump float vSpecular;\n
193   uniform sampler2D sDiffuse;\n
194   uniform lowp vec4 uColor;\n
195
196   void main()\n
197   {\n
198     vec4 texture = texture2D( sDiffuse, vTexCoord );\n
199     gl_FragColor = vec4( vIllumination.rgb * texture.rgb * uColor.rgb + vSpecular * 0.3, texture.a * uColor.a);\n
200   }\n
201 );
202
203 //  Diffuse and specular illumination shader with albedo texture, normal map and gloss map shader
204
205 const char* NRMMAP_VERTEX_SHADER = MAKE_SHADER(
206   attribute highp vec3 aPosition;\n
207   attribute highp vec2 aTexCoord;\n
208   attribute highp vec3 aNormal;\n
209   attribute highp vec3 aTangent;\n
210   attribute highp vec3 aBiNormal;\n
211   varying mediump vec2 vTexCoord;\n
212   varying mediump vec3 vLightDirection;\n
213   varying mediump vec3 vHalfVector;\n
214   uniform mediump vec3 uSize;\n
215   uniform mediump mat4 uMvpMatrix;\n
216   uniform mediump mat4 uModelView;
217   uniform mediump mat3 uNormalMatrix;
218   uniform mediump mat4 uObjectMatrix;\n
219   uniform mediump vec3 uLightPosition;\n
220
221   void main()
222   {\n
223     vec4 vertexPosition = vec4(aPosition*min(uSize.x, uSize.y), 1.0);\n
224     vertexPosition = uObjectMatrix * vertexPosition;\n
225     vertexPosition = uMvpMatrix * vertexPosition;\n
226
227     vec4 vertPos = uModelView * vec4(aPosition.xyz, 1.0);\n
228     vec4 lightPos = uModelView * vec4(uLightPosition, 1.0);\n
229
230     vec3 tangent = normalize(uNormalMatrix * aTangent);
231     vec3 binormal = normalize(uNormalMatrix * aBiNormal);
232     vec3 normal = normalize(uNormalMatrix * aNormal);
233
234     vec3 vecToLight = normalize( lightPos.xyz - vertPos.xyz );\n
235     vLightDirection.x = dot(vecToLight, tangent);
236     vLightDirection.y = dot(vecToLight, binormal);
237     vLightDirection.z = dot(vecToLight, normal);
238
239     vec3 viewDir = normalize(-vertPos.xyz);
240     vec3 halfVector = normalize(viewDir + vecToLight);
241     vHalfVector.x = dot(halfVector, tangent);
242     vHalfVector.y = dot(halfVector, binormal);
243     vHalfVector.z = dot(halfVector, normal);
244
245     vTexCoord = aTexCoord;\n
246     gl_Position = vertexPosition;\n
247   }\n
248 );
249
250 const char* NRMMAP_FRAGMENT_SHADER = MAKE_SHADER(
251   precision mediump float;\n
252   varying mediump vec2 vTexCoord;\n
253   varying mediump vec3 vLightDirection;\n
254   varying mediump vec3 vHalfVector;\n
255   uniform sampler2D sDiffuse;\n
256   uniform sampler2D sNormal;\n
257   uniform sampler2D sGloss;\n
258   uniform lowp vec4 uColor;\n
259
260   void main()\n
261   {\n
262     vec4 texture = texture2D( sDiffuse, vTexCoord );\n
263     vec3 normal = normalize( texture2D( sNormal, vTexCoord ).xyz * 2.0 - 1.0 );\n
264     vec4 glossMap = texture2D( sGloss, vTexCoord );\n
265
266     float lightDiffuse = max( 0.0, dot( normal, normalize(vLightDirection) ) );\n
267     lightDiffuse = lightDiffuse * 0.5 + 0.5;\n
268
269     float shininess = pow (max (dot (normalize( vHalfVector ), normal), 0.0), 16.0)  ;
270
271     gl_FragColor = vec4( texture.rgb * uColor.rgb * lightDiffuse + shininess * glossMap.rgb, texture.a * uColor.a);\n
272   }\n
273 );
274
275
276 } // anonymous namespace
277
278 using namespace Dali;
279
280 void LookAt(Matrix& result, const Vector3& eye, const Vector3& target, const Vector3& up)
281 {
282   Vector3 vZ = target - eye;
283   vZ.Normalize();
284
285   Vector3 vX = up.Cross(vZ);
286   vX.Normalize();
287
288   Vector3 vY = vZ.Cross(vX);
289   vY.Normalize();
290
291   result.SetInverseTransformComponents(vX, vY, vZ, eye);
292 }
293
294
295 Model3dView::Model3dView()
296   : Control( ControlBehaviour( ACTOR_BEHAVIOUR_NONE ) )
297 {
298   mIlluminationType = Toolkit::Model3dView::DIFFUSE_WITH_NORMAL_MAP;
299
300   mCameraFOV = Math::PI_OVER_180 * 45.f;
301
302   mControlSize = Vector2(100.,100.);
303 }
304
305 Model3dView::~Model3dView()
306 {
307 }
308
309 Toolkit::Model3dView Model3dView::New()
310 {
311   Model3dView* impl = new Model3dView();
312
313   Dali::Toolkit::Model3dView handle = Dali::Toolkit::Model3dView( *impl );
314
315   // Second-phase init of the implementation
316   // This can only be done after the CustomActor connection has been made...
317   impl->Initialize();
318
319   return handle;
320 }
321
322 void Model3dView::SetProperty( BaseObject* object, Property::Index index, const Property::Value& value )
323 {
324   Toolkit::Model3dView model3dView = Toolkit::Model3dView::DownCast( Dali::BaseHandle( object ) );
325
326   if( model3dView )
327   {
328     Model3dView& impl( GetImpl( model3dView ) );
329     switch( index )
330     {
331       case Toolkit::Model3dView::Property::GEOMETRY_URL:
332       {
333         if( value.Get(impl.mObjUrl) )
334         {
335           impl.LoadGeometry();
336           impl.CreateGeometry();
337         }
338         break;
339       }
340       case Toolkit::Model3dView::Property::MATERIAL_URL:
341       {
342         if( value.Get(impl.mTextureSetUrl) )
343         {
344           impl.LoadMaterial();
345           impl.CreateMaterial();
346         }
347         break;
348       }
349       case Toolkit::Model3dView::Property::IMAGES_URL:
350       {
351         if( value.Get(impl.mImagesUrl) )
352         {
353           impl.LoadTextures();
354         }
355         break;
356       }
357       case Toolkit::Model3dView::Property::ILLUMINATION_TYPE:
358       {
359         int illuminationType;
360         if( value.Get(illuminationType) )
361         {
362           impl.mIlluminationType = Toolkit::Model3dView::IlluminationType(illuminationType);
363           impl.CreateGeometry();
364           impl.CreateMaterial();
365           impl.LoadTextures();
366         }
367         break;
368       }
369       case Toolkit::Model3dView::Property::TEXTURE0_URL:
370       {
371         value.Get(impl.mTexture0Url);
372         break;
373       }
374       case Toolkit::Model3dView::Property::TEXTURE1_URL:
375       {
376         value.Get(impl.mTexture1Url);
377         break;
378       }
379       case Toolkit::Model3dView::Property::TEXTURE2_URL:
380       {
381         value.Get(impl.mTexture2Url);
382         break;
383       }
384     }
385   }
386 }
387
388 Property::Value Model3dView::GetProperty( BaseObject* object, Property::Index index )
389 {
390   Property::Value value;
391
392   Toolkit::Model3dView model3dView = Toolkit::Model3dView::DownCast( Dali::BaseHandle( object ) );
393
394   if( model3dView )
395   {
396     Model3dView& impl( GetImpl( model3dView ) );
397     switch( index )
398     {
399       case Toolkit::Model3dView::Property::GEOMETRY_URL:
400       {
401         value = impl.mObjUrl;
402         break;
403       }
404       case Toolkit::Model3dView::Property::MATERIAL_URL:
405       {
406         value = impl.mTextureSetUrl;
407         break;
408       }
409       case Toolkit::Model3dView::Property::IMAGES_URL:
410       {
411         value = impl.mImagesUrl;
412         break;
413       }
414       case Toolkit::Model3dView::Property::ILLUMINATION_TYPE:
415       {
416         value = int(impl.mIlluminationType);
417         break;
418       }
419       case Toolkit::Model3dView::Property::TEXTURE0_URL:
420       {
421         value = impl.mTexture0Url;
422         break;
423       }
424       case Toolkit::Model3dView::Property::TEXTURE1_URL:
425       {
426         value = impl.mTexture1Url;
427         break;
428       }
429       case Toolkit::Model3dView::Property::TEXTURE2_URL:
430       {
431         value = impl.mTexture2Url;
432         break;
433       }
434     }
435   }
436
437   return value;
438 }
439
440 /////////////////////////////////////////////////////////////
441
442
443 void Model3dView::OnStageConnection( int depth )
444 {
445   Control::OnStageConnection( depth );
446
447   CustomActor self = Self();
448   self.AddRenderer( mRenderer );
449
450   if( mObjLoader.IsSceneLoaded() )
451   {
452     mMesh = mObjLoader.CreateGeometry( GetShaderProperties( mIlluminationType ) );
453
454     CreateMaterial();
455     LoadTextures();
456
457     mRenderer.SetGeometry( mMesh );
458
459     //create constraint for lightPosition Property with uLightPosition in the shader
460     Vector3 lightPosition( 0, 0, 0 );
461     Dali::Property::Index lightProperty = mShader.RegisterProperty( "uLightPosition", lightPosition );
462     Constraint constraint = Constraint::New<Vector3>( mShader, lightProperty, EqualToConstraint() );
463     constraint.AddSource( Source( self, Toolkit::Model3dView::Property::LIGHT_POSITION ) );
464     constraint.Apply();
465   }
466 }
467
468 ///////////////////////////////////////////////////////////
469 //
470 // Private methods
471 //
472
473 void Model3dView::OnInitialize()
474 {
475   //Create empty versions of the geometry and material so we always have a Renderer
476   Geometry mesh = Geometry::New();
477   Shader shader = Shader::New( SIMPLE_VERTEX_SHADER, SIMPLE_FRAGMENT_SHADER );
478   mRenderer = Renderer::New( mesh, shader );
479
480 }
481
482 void Model3dView::LoadGeometry()
483 {
484   //Load file in adaptor
485   std::streampos fileSize;
486   Dali::Vector<char> fileContent;
487
488   if (FileLoader::ReadFile(mObjUrl,fileSize,fileContent,FileLoader::TEXT))
489   {
490     mObjLoader.ClearArrays();
491     mObjLoader.LoadObject(fileContent.Begin(), fileSize);
492
493     //Get size information from the obj loaded
494     mSceneCenter = mObjLoader.GetCenter();
495     mSceneSize = mObjLoader.GetSize();
496   }
497   else
498   {
499     //Error
500   }
501 }
502
503 void Model3dView::LoadMaterial()
504 {
505   //Load file in adaptor
506   std::streampos fileSize;
507   Dali::Vector<char> fileContent;
508
509   if( FileLoader::ReadFile(mTextureSetUrl, fileSize, fileContent, FileLoader::TEXT) )
510   {
511     mObjLoader.LoadMaterial(fileContent.Begin(), fileSize, mTexture0Url, mTexture1Url, mTexture2Url);
512   }
513   else
514   {
515     //Error
516   }
517 }
518
519 void Model3dView::Load()
520 {
521   LoadGeometry();
522   LoadMaterial();
523 }
524
525 void Model3dView::OnRelayout( const Vector2& size, RelayoutContainer& container )
526 {
527   UpdateView();
528 }
529
530 void Model3dView::UpdateView()
531 {
532   if( mObjLoader.IsSceneLoaded() )
533   {
534     //The object will always be centred
535
536     Matrix scaleMatrix;
537     scaleMatrix.SetIdentityAndScale(Vector3(1.0, -1.0, 1.0));
538
539     mShader.RegisterProperty( "uObjectMatrix", scaleMatrix );
540   }
541 }
542
543 void Model3dView::CreateGeometry()
544 {
545   if( mObjLoader.IsSceneLoaded() )
546   {
547     mMesh = mObjLoader.CreateGeometry( GetShaderProperties( mIlluminationType ) );
548
549     if( mRenderer )
550     {
551       mRenderer.SetGeometry( mMesh );
552       mRenderer.SetProperty( Renderer::Property::DEPTH_WRITE_MODE, DepthWriteMode::ON );
553     }
554   }
555 }
556
557 void Model3dView::UpdateShaderUniforms()
558 {
559   if( mShader )
560   {
561     //Update shader related info, uniforms, etc. for the new shader
562     UpdateView();
563
564     Vector3 lightPosition( 0, 0, 0 );
565     Dali::Property::Index lightProperty = mShader.RegisterProperty( "uLightPosition", lightPosition );
566
567     CustomActor self = Self();
568
569     //create constraint for lightPosition Property with uLightPosition in the shader
570     if( lightProperty )
571     {
572       Constraint constraint = Constraint::New<Vector3>( mShader, lightProperty, EqualToConstraint() );
573       constraint.AddSource( Source( self, Toolkit::Model3dView::Property::LIGHT_POSITION ) );
574       constraint.Apply();
575     }
576   }
577 }
578
579 void Model3dView::CreateMaterial()
580 {
581   if( mObjLoader.IsMaterialLoaded() && (mTexture0Url != "") && mObjLoader.IsTexturePresent() )
582   {
583     if( (mTexture2Url != "") && (mTexture1Url != "") && (mIlluminationType == Toolkit::Model3dView::DIFFUSE_WITH_NORMAL_MAP) )
584     {
585       mShader = Shader::New( NRMMAP_VERTEX_SHADER, NRMMAP_FRAGMENT_SHADER );
586     }
587     else if( mIlluminationType == Toolkit::Model3dView::DIFFUSE_WITH_TEXTURE ||
588              mIlluminationType == Toolkit::Model3dView::DIFFUSE_WITH_NORMAL_MAP )
589     {
590       mShader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
591     }
592     else
593     {
594       mShader = Shader::New( SIMPLE_VERTEX_SHADER, SIMPLE_FRAGMENT_SHADER );
595     }
596   }
597   else
598   {
599     mShader = Shader::New( SIMPLE_VERTEX_SHADER, SIMPLE_FRAGMENT_SHADER );
600   }
601
602   mTextureSet = TextureSet::New();
603
604   if( mRenderer )
605   {
606     mRenderer.SetTextures( mTextureSet );
607     mRenderer.SetShader( mShader );
608     mRenderer.SetProperty( Renderer::Property::FACE_CULLING_MODE, FaceCullingMode::BACK );
609   }
610
611   UpdateShaderUniforms();
612 }
613
614 void Model3dView::LoadTextures()
615 {
616   if( !mTextureSet )
617   {
618     return;
619   }
620
621   Sampler sampler = Sampler::New();
622   sampler.SetFilterMode( FilterMode::LINEAR_MIPMAP_LINEAR, FilterMode::LINEAR_MIPMAP_LINEAR );
623
624   // Setup diffuse texture.
625   if( !mTexture0Url.empty() && ( mIlluminationType != Toolkit::Model3dView::DIFFUSE ) )
626   {
627     std::string imageUrl = mImagesUrl + mTexture0Url;
628
629     //Load textures
630     Texture diffuseTexture = LoadTexture( imageUrl.c_str() );
631     if( diffuseTexture )
632     {
633       mTextureSet.SetTexture( DIFFUSE_TEXTURE_INDEX, diffuseTexture );
634       mTextureSet.SetSampler( DIFFUSE_TEXTURE_INDEX, sampler );
635     }
636   }
637
638   if( mIlluminationType == Toolkit::Model3dView::DIFFUSE_WITH_NORMAL_MAP )
639   {
640     // Setup normal map texture.
641     if( !mTexture1Url.empty() )
642     {
643       std::string imageUrl = mImagesUrl + mTexture1Url;
644
645       //Load textures
646       Texture normalTexture = LoadTexture( imageUrl.c_str() );
647       if( normalTexture )
648       {
649         mTextureSet.SetTexture( NORMAL_TEXTURE_INDEX, normalTexture );
650         mTextureSet.SetSampler( NORMAL_TEXTURE_INDEX, sampler );
651       }
652     }
653     if( !mTexture2Url.empty() )
654     {
655       // Setup gloss map texture.
656       std::string imageUrl = mImagesUrl + mTexture2Url;
657
658       //Load textures
659       Texture glossTexture = LoadTexture( imageUrl.c_str() );
660       if( glossTexture )
661       {
662         mTextureSet.SetTexture( GLOSS_TEXTURE_INDEX, glossTexture );
663         mTextureSet.SetSampler( GLOSS_TEXTURE_INDEX, sampler );
664       }
665     }
666   }
667 }
668
669 int Model3dView::GetShaderProperties( Toolkit::Model3dView::IlluminationType illuminationType )
670 {
671   int objectProperties = 0;
672
673   if( illuminationType == Toolkit::Model3dView::DIFFUSE_WITH_TEXTURE ||
674       illuminationType == Toolkit::Model3dView::DIFFUSE_WITH_NORMAL_MAP )
675   {
676     objectProperties |= ObjLoader::TEXTURE_COORDINATES;
677   }
678
679   if( illuminationType == Toolkit::Model3dView::DIFFUSE_WITH_NORMAL_MAP )
680   {
681     objectProperties |= ObjLoader::TANGENTS | ObjLoader::BINORMALS;
682   }
683
684   return objectProperties;
685 }
686
687 } // namespace Internal
688 } // namespace Toolkit
689 } // namespace Dali