2 * Copyright (c) 2021 Samsung Electronics Co., Ltd.
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
8 * http://www.apache.org/licenses/LICENSE-2.0
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.
19 #include "border-visual.h"
22 #include <dali/devel-api/rendering/renderer-devel.h>
23 #include <dali/integration-api/debug.h>
26 #include <dali-toolkit/internal/graphics/builtin-shader-extern-gen.h>
27 #include <dali-toolkit/internal/visuals/visual-base-data-impl.h>
28 #include <dali-toolkit/internal/visuals/visual-factory-cache.h>
29 #include <dali-toolkit/internal/visuals/visual-factory-impl.h>
30 #include <dali-toolkit/internal/visuals/visual-string-constants.h>
31 #include <dali-toolkit/public-api/visuals/border-visual-properties.h>
32 #include <dali-toolkit/public-api/visuals/visual-properties.h>
42 const char* const POSITION_ATTRIBUTE_NAME("aPosition");
43 const char* const DRIFT_ATTRIBUTE_NAME("aDrift");
44 const char* const INDEX_NAME("indices");
47 BorderVisualPtr BorderVisual::New(VisualFactoryCache& factoryCache, const Property::Map& properties)
49 BorderVisualPtr borderVisualPtr(new BorderVisual(factoryCache));
50 borderVisualPtr->SetProperties(properties);
51 borderVisualPtr->Initialize();
52 return borderVisualPtr;
55 BorderVisual::BorderVisual(VisualFactoryCache& factoryCache)
56 : Visual::Base(factoryCache, Visual::FittingMode::FILL, Toolkit::Visual::BORDER),
57 mBorderColor(Color::TRANSPARENT),
59 mBorderColorIndex(Property::INVALID_INDEX),
60 mBorderSizeIndex(Property::INVALID_INDEX),
65 BorderVisual::~BorderVisual()
69 void BorderVisual::DoSetProperties(const Property::Map& propertyMap)
71 for(Property::Map::SizeType iter = 0; iter < propertyMap.Count(); ++iter)
73 KeyValuePair keyValue = propertyMap.GetKeyValue(iter);
74 if(keyValue.first.type == Property::Key::INDEX)
76 DoSetProperty(keyValue.first.indexKey, keyValue.second);
80 if(keyValue.first == COLOR_NAME)
82 DoSetProperty(Toolkit::BorderVisual::Property::COLOR, keyValue.second);
84 else if(keyValue.first == SIZE_NAME)
86 DoSetProperty(Toolkit::BorderVisual::Property::SIZE, keyValue.second);
88 else if(keyValue.first == ANTI_ALIASING)
90 DoSetProperty(Toolkit::BorderVisual::Property::ANTI_ALIASING, keyValue.second);
96 void BorderVisual::DoSetProperty(Dali::Property::Index index,
97 const Dali::Property::Value& value)
101 case Toolkit::BorderVisual::Property::COLOR:
103 if(!value.Get(mBorderColor))
105 DALI_LOG_ERROR("BorderVisual: borderColor property has incorrect type\n");
109 case Toolkit::BorderVisual::Property::SIZE:
111 if(!value.Get(mBorderSize))
113 DALI_LOG_ERROR("BorderVisual: borderSize property has incorrect type\n");
117 case Toolkit::BorderVisual::Property::ANTI_ALIASING:
119 if(!value.Get(mAntiAliasing))
121 DALI_LOG_ERROR("BorderVisual: antiAliasing property has incorrect type\n");
128 void BorderVisual::DoSetOnScene(Actor& actor)
130 mBorderColorIndex = mImpl->mRenderer.RegisterProperty(Toolkit::BorderVisual::Property::COLOR, COLOR_NAME, mBorderColor);
131 if(mBorderColor.a < 1.f || mAntiAliasing)
133 mImpl->mRenderer.SetProperty(Renderer::Property::BLEND_MODE, BlendMode::ON);
135 mBorderSizeIndex = mImpl->mRenderer.RegisterProperty(Toolkit::BorderVisual::Property::SIZE, SIZE_NAME, mBorderSize);
137 actor.AddRenderer(mImpl->mRenderer);
139 // Border Visual Generated and ready to display
140 ResourceReady(Toolkit::Visual::ResourceStatus::READY);
143 void BorderVisual::DoCreatePropertyMap(Property::Map& map) const
146 map.Insert(Toolkit::Visual::Property::TYPE, Toolkit::Visual::BORDER);
147 map.Insert(Toolkit::BorderVisual::Property::COLOR, mBorderColor);
148 map.Insert(Toolkit::BorderVisual::Property::SIZE, mBorderSize);
149 map.Insert(Toolkit::BorderVisual::Property::ANTI_ALIASING, mAntiAliasing);
152 void BorderVisual::DoCreateInstancePropertyMap(Property::Map& map) const
157 void BorderVisual::OnSetTransform()
161 mImpl->mTransform.RegisterUniforms(mImpl->mRenderer, Direction::LEFT_TO_RIGHT);
165 void BorderVisual::OnInitialize()
167 Geometry geometry = mFactoryCache.GetGeometry(VisualFactoryCache::BORDER_GEOMETRY);
170 geometry = CreateBorderGeometry();
171 mFactoryCache.SaveGeometry(VisualFactoryCache::BORDER_GEOMETRY, geometry);
174 Shader shader = GetBorderShader();
175 mImpl->mRenderer = Renderer::New(geometry, shader);
177 //Register transform properties
178 mImpl->mTransform.RegisterUniforms(mImpl->mRenderer, Direction::LEFT_TO_RIGHT);
181 Shader BorderVisual::GetBorderShader()
186 shader = mFactoryCache.GetShader(VisualFactoryCache::BORDER_SHADER_ANTI_ALIASING);
189 shader = Shader::New(Dali::Shader::GetVertexShaderPrefix() + SHADER_BORDER_VISUAL_ANTI_ALIASING_SHADER_VERT.data(), Dali::Shader::GetFragmentShaderPrefix() + SHADER_BORDER_VISUAL_ANTI_ALIASING_SHADER_FRAG.data());
190 mFactoryCache.SaveShader(VisualFactoryCache::BORDER_SHADER_ANTI_ALIASING, shader);
195 shader = mFactoryCache.GetShader(VisualFactoryCache::BORDER_SHADER);
198 shader = Shader::New(Dali::Shader::GetVertexShaderPrefix() + SHADER_BORDER_VISUAL_SHADER_VERT.data(), Dali::Shader::GetFragmentShaderPrefix() + SHADER_BORDER_VISUAL_SHADER_FRAG.data());
199 mFactoryCache.SaveShader(VisualFactoryCache::BORDER_SHADER, shader);
207 * Vertices and triangles of the border geometry:
209 * vertex position = aPosition*uSize.xy + aDrift*uBorderSize;
222 Geometry BorderVisual::CreateBorderGeometry()
224 const float halfWidth = 0.5f;
225 const float halfHeight = 0.5f;
231 BorderVertex borderVertexData[16] =
233 {Vector2(-halfWidth, -halfHeight), Vector2(0.f, 0.f)},
234 {Vector2(-halfWidth, -halfHeight), Vector2(1.f, 0.f)},
235 {Vector2(halfWidth, -halfHeight), Vector2(-1.f, 0.f)},
236 {Vector2(halfWidth, -halfHeight), Vector2(0.f, 0.f)},
238 {Vector2(-halfWidth, -halfHeight), Vector2(0.f, 1.f)},
239 {Vector2(-halfWidth, -halfHeight), Vector2(1.f, 1.f)},
240 {Vector2(halfWidth, -halfHeight), Vector2(-1.f, 1.f)},
241 {Vector2(halfWidth, -halfHeight), Vector2(0.f, 1.f)},
243 {Vector2(-halfWidth, halfHeight), Vector2(0.f, -1.f)},
244 {Vector2(-halfWidth, halfHeight), Vector2(1.f, -1.f)},
245 {Vector2(halfWidth, halfHeight), Vector2(-1.f, -1.f)},
246 {Vector2(halfWidth, halfHeight), Vector2(0.f, -1.f)},
248 {Vector2(-halfWidth, halfHeight), Vector2(0.f, 0.f)},
249 {Vector2(-halfWidth, halfHeight), Vector2(1.f, 0.f)},
250 {Vector2(halfWidth, halfHeight), Vector2(-1.f, 0.f)},
251 {Vector2(halfWidth, halfHeight), Vector2(0.f, 0.f)},
254 Property::Map borderVertexFormat;
255 borderVertexFormat[POSITION_ATTRIBUTE_NAME] = Property::VECTOR2;
256 borderVertexFormat[DRIFT_ATTRIBUTE_NAME] = Property::VECTOR2;
257 VertexBuffer borderVertices = VertexBuffer::New(borderVertexFormat);
258 borderVertices.SetData(borderVertexData, 16);
261 unsigned short indexData[24] = {1, 5, 2, 6, 3, 7, 7, 6, 11, 10, 15, 14, 14, 10, 13, 9, 12, 8, 8, 9, 4, 5, 0, 1};
263 // Create the geometry object
264 Geometry geometry = Geometry::New();
265 geometry.AddVertexBuffer(borderVertices);
266 geometry.SetIndexBuffer(indexData, sizeof(indexData) / sizeof(indexData[0]));
267 geometry.SetType(Geometry::TRIANGLE_STRIP);
272 } // namespace Internal
274 } // namespace Toolkit