float yBearing; ///< The distance from the baseline to the topmost border of the glyph
float advance; ///< The distance to move the cursor for this glyph
float scaleFactor; ///< The scaling applied (fixed-size fonts only)
+ bool softwareItalic; ///< Whether glyph needs software support to draw italic style
+ bool softwareBold; ///< Whether glyph needs software support to draw bold style
};
bool IsEqualGlyph ( const GlyphInfoData& glyphData, const GlyphInfo& glyph )
{
return false;
}
+ if( glyphData.softwareItalic != glyph.softwareItalic )
+ {
+ return false;
+ }
+ if( glyphData.softwareBold != glyph.softwareBold )
+ {
+ return false;
+ }
return true;
}
Length* charactersPerGlyph; ///< The characters per glyph.
uint32_t expectedNumberOfNewParagraphGlyphs; ///< The expected number of glyphs.
GlyphIndex* newParagraphGlyphs; ///< Indices to the new paragraphs glyphs.
+ Vector<FontDescriptionRun> fontDescriptions; ///< Fonts which is used for text.
};
bool ShapeInfoTest( const ShapeInfoData& data )
const LayoutOptions options;
CreateTextModel( data.text,
textArea,
- fontDescriptions,
+ data.fontDescriptions,
options,
layoutSize,
logicalModel,
tet_result(TET_PASS);
END_TEST;
}
+
+int UtcDaliTextSoftwareStyling(void)
+{
+ tet_infoline(" UtcDaliTextSoftwareStyling");
+
+ struct GlyphInfoData glyphs01[] =
+ {
+ { 2u, 14750u, 0.f, 0.f, 0.f, 0.f, 16.f, 0.f, true, true },
+ { 2u, 9802u, 0.f, 0.f, 0.f, 0.f, 16.f, 0.f, true, true },
+ { 2u, 12811u, 0.f, 0.f, 0.f, 0.f, 16.f, 0.f, true, true },
+ };
+ struct GlyphInfoData glyphs02[] =
+ {
+ { 2u, 14750u, 0.f, 0.f, 0.f, 0.f, 16.f, 0.f, false, false },
+ { 2u, 9802u, 0.f, 0.f, 0.f, 0.f, 16.f, 0.f, false, true },
+ { 2u, 12811u, 0.f, 0.f, 0.f, 0.f, 16.f, 0.f, true, false },
+ };
+
+ CharacterIndex characterIndices[] = { 0u, 1u, 2u };
+ Length charactersPerGlyph[] = { 1u, 1u, 1u };
+
+ Vector<FontDescriptionRun> fontDescriptions01;
+ Vector<FontDescriptionRun> fontDescriptions02;
+
+ FontDescriptionRun fontDescriptionRun01 =
+ {
+ {
+ 0u,
+ 3u
+ },
+ NULL,
+ 0u,
+ TextAbstraction::FontWeight::BOLD,
+ TextAbstraction::FontWidth::NONE,
+ TextAbstraction::FontSlant::ITALIC,
+ TextAbstraction::FontClient::DEFAULT_POINT_SIZE,
+ false,
+ true,
+ false,
+ true,
+ false
+ };
+ fontDescriptions01.PushBack(fontDescriptionRun01);
+
+ FontDescriptionRun fontDescriptionRun02 =
+ {
+ {
+ 0u,
+ 1u
+ },
+ NULL,
+ 0u,
+ TextAbstraction::FontWeight::NONE,
+ TextAbstraction::FontWidth::NONE,
+ TextAbstraction::FontSlant::NONE,
+ TextAbstraction::FontClient::DEFAULT_POINT_SIZE,
+ false,
+ false,
+ false,
+ false,
+ false
+ };
+ FontDescriptionRun fontDescriptionRun03 =
+ {
+ {
+ 1u,
+ 1u
+ },
+ NULL,
+ 0u,
+ TextAbstraction::FontWeight::BOLD,
+ TextAbstraction::FontWidth::NONE,
+ TextAbstraction::FontSlant::NONE,
+ TextAbstraction::FontClient::DEFAULT_POINT_SIZE,
+ false,
+ true,
+ false,
+ false,
+ false
+ };
+ FontDescriptionRun fontDescriptionRun04 =
+ {
+ {
+ 2u,
+ 1u
+ },
+ NULL,
+ 0u,
+ TextAbstraction::FontWeight::NONE,
+ TextAbstraction::FontWidth::NONE,
+ TextAbstraction::FontSlant::ITALIC,
+ TextAbstraction::FontClient::DEFAULT_POINT_SIZE,
+ false,
+ false,
+ false,
+ true,
+ false
+ };
+
+ fontDescriptions02.PushBack(fontDescriptionRun02);
+ fontDescriptions02.PushBack(fontDescriptionRun03);
+ fontDescriptions02.PushBack(fontDescriptionRun04);
+
+
+ struct ShapeInfoData data[] =
+ {
+ {
+ "Chiness script. Characters have same font description",
+ "未取得",
+ 0u,
+ 3u,
+ 3u,
+ glyphs01,
+ characterIndices,
+ charactersPerGlyph,
+ 0u,
+ NULL,
+ fontDescriptions01
+ },
+ {
+ "Chiness script. Each character has different font description.",
+ "未取得",
+ 0u,
+ 3u,
+ 3u,
+ glyphs02,
+ characterIndices,
+ charactersPerGlyph,
+ 0u,
+ NULL,
+ fontDescriptions02
+ }
+ };
+
+ const unsigned int numberOfTests = 2u;
+
+ for( unsigned int index = 0u; index < numberOfTests; ++index )
+ {
+ ToolkitTestApplication application;
+ if( !ShapeInfoTest( data[index] ) )
+ {
+ tet_result(TET_FAIL);
+ }
+ }
+
+ tet_result(TET_PASS);
+ END_TEST;
+}
\ No newline at end of file
utc-Dali-FlexContainer.cpp
utc-Dali-FlexLayout.cpp
utc-Dali-GaussianBlurView.cpp
+ utc-Dali-GridLayout.cpp
utc-Dali-ImageView.cpp
utc-Dali-ImageVisual.cpp
utc-Dali-JsonParser.cpp
void GetFontMetrics( FontId fontId, FontMetrics& metrics ){}
GlyphIndex GetGlyphIndex( FontId fontId, Character charcode ){return 0;}
bool GetGlyphMetrics( GlyphInfo* array, uint32_t size, bool horizontal ){return true;}
- void CreateBitmap( FontId fontId, GlyphIndex glyphIndex, Dali::TextAbstraction::FontClient::GlyphBufferData& data, int outlineWidth ){}
+ void CreateBitmap( FontId fontId, GlyphIndex glyphIndex, bool softwareItailc, bool softwareBold, Dali::TextAbstraction::FontClient::GlyphBufferData& data, int outlineWidth ){}
PixelData CreateBitmap( FontId fontId, GlyphIndex glyphIndex, int outlineWidth ){return PixelData();}
void CreateVectorBlob( FontId fontId, GlyphIndex glyphIndex, VectorBlob*& blob,
unsigned int& blobLength, unsigned int& nominalWidth, unsigned int& nominalHeight )
return GetImplementation(*this).GetGlyphMetrics( array, size, horizontal );
}
-void FontClient::CreateBitmap( FontId fontId, GlyphIndex glyphIndex, Dali::TextAbstraction::FontClient::GlyphBufferData& data, int outlineWidth )
+void FontClient::CreateBitmap( FontId fontId, GlyphIndex glyphIndex, bool softwareItailc, bool softwareBold, Dali::TextAbstraction::FontClient::GlyphBufferData& data, int outlineWidth )
{
- GetImplementation(*this).CreateBitmap( fontId, glyphIndex, data, outlineWidth );
+ GetImplementation(*this).CreateBitmap( fontId, glyphIndex, softwareItailc, softwareBold, data, outlineWidth );
}
PixelData FontClient::CreateBitmap( FontId fontId, GlyphIndex glyphIndex, int outlineWidth )
--- /dev/null
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include <iostream>
+#include <stdlib.h>
+#include <dali-toolkit-test-suite-utils.h>
+#include <toolkit-event-thread-callback.h>
+
+#include <dali-toolkit/dali-toolkit.h>
+#include <dali-toolkit/devel-api/controls/control-devel.h>
+#include <dali-toolkit/devel-api/layouting/absolute-layout.h>
+#include <dali-toolkit/devel-api/layouting/grid.h>
+#include <dali-toolkit/devel-api/layouting/layout-item-impl.h>
+#include <dali-toolkit/devel-api/layouting/layout-group-impl.h>
+
+#include <../custom-layout.h>
+
+#include <layout-utils.h>
+
+using namespace Dali;
+using namespace Toolkit;
+
+void utc_dali_toolkit_grid_layouting_startup(void)
+{
+ test_return_value = TET_UNDEF;
+}
+
+void utc_dali_toolkit_grid_layouting_cleanup(void)
+{
+ test_return_value = TET_PASS;
+}
+
+int UtcDaliLayouting_GridLayout01(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliLayouting_GridLayout01 2 Column, 4 Items");
+
+ const auto NUMBER_OF_COLUMNS = 2;
+ const auto NUMBER_OF_ITEMS = 4;
+
+ tet_printf( "Testing %d columns with %d items\n", NUMBER_OF_COLUMNS, NUMBER_OF_ITEMS );
+
+ Stage stage = Stage::GetCurrent();
+
+ auto rootControl = Control::New();
+ auto absoluteLayout = AbsoluteLayout::New();
+ DevelControl::SetLayout( rootControl, absoluteLayout );
+ rootControl.SetName( "AbsoluteLayout" );
+ stage.Add( rootControl );
+
+ auto gridContainer = Control::New();
+ auto gridLayout = Grid::New();
+ gridLayout.SetNumberOfColumns( NUMBER_OF_COLUMNS );
+ gridContainer.SetName( "GridLayout");
+ DevelControl::SetLayout( gridContainer, gridLayout );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::WIDTH_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::HEIGHT_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+
+ std::vector< Control > controls;
+ for( auto i=0; i < NUMBER_OF_ITEMS; i++ )
+ {
+ controls.push_back( CreateLeafControl( 100, 100 ) );
+ }
+
+ for( auto&& iter : controls )
+ {
+ gridContainer.Add( iter );
+ }
+
+ rootControl.Add( gridContainer );
+
+ // Ensure layouting happens
+ application.SendNotification();
+ application.Render();
+
+ // Grid will layout first 2 items on first row then last 2 on second row.
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 100.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ // Item sizes will not be changed
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ tet_printf( "Confirm number of columns is as set\n");
+ DALI_TEST_EQUALS( gridLayout.GetNumberOfColumns(), NUMBER_OF_COLUMNS, TEST_LOCATION );
+
+ END_TEST;
+}
+
+int UtcDaliLayouting_GridLayout02(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline("UtcDaliLayouting_GridLayout02");
+
+ const auto NUMBER_OF_COLUMNS = 3;
+ const auto NUMBER_OF_ITEMS = 7;
+
+ tet_printf( "Testing %d columns with %d items\n", NUMBER_OF_COLUMNS, NUMBER_OF_ITEMS );
+
+ Stage stage = Stage::GetCurrent();
+
+ auto rootControl = Control::New();
+ auto absoluteLayout = AbsoluteLayout::New();
+ DevelControl::SetLayout( rootControl, absoluteLayout );
+ rootControl.SetName( "AbsoluteLayout" );
+ stage.Add( rootControl );
+
+ auto gridContainer = Control::New();
+ auto gridLayout = Grid::New();
+ gridLayout.SetNumberOfColumns( NUMBER_OF_COLUMNS );
+ gridContainer.SetName( "GridLayout");
+ DevelControl::SetLayout( gridContainer, gridLayout );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::WIDTH_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::HEIGHT_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+
+ std::vector< Control > controls;
+ for( auto i=0; i < NUMBER_OF_ITEMS; i++ )
+ {
+ controls.push_back( CreateLeafControl( 100, 100 ) );
+ }
+
+ for( auto&& iter : controls )
+ {
+ gridContainer.Add( iter );
+ }
+
+ rootControl.Add( gridContainer );
+
+ // Ensure layouting happens
+ application.SendNotification();
+ application.Render();
+
+ // grid layouts out 3 items per row, which is 480x800.
+ // Row 1
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 100.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 200.0f, 0.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ // Row 2
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[4].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[5].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 200.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ // Row 3
+ DALI_TEST_EQUALS( controls[6].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f, 200.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[4].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[5].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[6].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ END_TEST;
+}
+
+int UtcDaliLayouting_GridLayout03(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliLayouting_GridLayout03 Grid Padding");
+
+ const auto NUMBER_OF_COLUMNS = 2;
+ const auto NUMBER_OF_ITEMS = 4;
+
+ tet_printf( "Testing %d columns with %d items\n", NUMBER_OF_COLUMNS, NUMBER_OF_ITEMS );
+
+ Extents GRID_PADDING( Extents( 10, 10, 20, 20 ) ); // start,end,top,bottom
+
+ tet_printf( "Testing with Padding 10,10,20,20\n");
+
+ Stage stage = Stage::GetCurrent();
+
+ auto rootControl = Control::New();
+ auto absoluteLayout = AbsoluteLayout::New();
+ DevelControl::SetLayout( rootControl, absoluteLayout );
+ rootControl.SetName( "AbsoluteLayout" );
+ stage.Add( rootControl );
+
+ auto gridContainer = Control::New();
+ auto gridLayout = Grid::New();
+ gridLayout.SetNumberOfColumns( NUMBER_OF_COLUMNS );
+ gridContainer.SetName( "GridLayout");
+ DevelControl::SetLayout( gridContainer, gridLayout );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::WIDTH_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::HEIGHT_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+ gridContainer.SetProperty( Control::Property::PADDING, GRID_PADDING );
+
+ std::vector< Control > controls;
+ for( auto i=0; i < NUMBER_OF_ITEMS; i++ )
+ {
+ controls.push_back( CreateLeafControl( 100, 100 ) );
+ }
+
+ for( auto&& iter : controls )
+ {
+ gridContainer.Add( iter );
+ }
+
+ rootControl.Add( gridContainer );
+
+ // Ensure layouting happens
+ application.SendNotification();
+ application.Render();
+
+ tet_infoline(" UtcDaliLayouting_GridLayout03 Grid Padding 2 Column, 4 Items");
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f + GRID_PADDING.start , 0.0f + GRID_PADDING.top, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 100.0f + GRID_PADDING.start, 0.0f + GRID_PADDING.top, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 0.0f + GRID_PADDING.start, 100.0f + GRID_PADDING.top , 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::POSITION ), Vector3( 100.0f + GRID_PADDING.start, 100.0f + GRID_PADDING.top, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ tet_infoline(" UtcDaliLayouting_GridLayout03 Size of Grid should include padding");
+ DALI_TEST_EQUALS( gridContainer.GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f * NUMBER_OF_COLUMNS + GRID_PADDING.start + + GRID_PADDING.end,
+ 100.0f * ( NUMBER_OF_ITEMS / NUMBER_OF_COLUMNS ) +
+ GRID_PADDING.top + GRID_PADDING.bottom,
+ 0.0f ), 0.0001f, TEST_LOCATION );
+
+ tet_infoline(" UtcDaliLayouting_GridLayout03 Item sizes unchanged");
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ END_TEST;
+}
+
+int UtcDaliLayouting_GridLayout04(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliLayouting_GridLayout04 Child Margin");
+
+ const auto NUMBER_OF_COLUMNS = 2;
+ const auto NUMBER_OF_ITEMS = 4;
+
+ tet_printf( "Testing %d columns with %d items\n", NUMBER_OF_COLUMNS, NUMBER_OF_ITEMS );
+
+ Extents GRID_PADDING( Extents( 10, 10, 20, 20 ) ); // start,end,top,bottom
+ Extents ITEM_MARGIN( Extents( 10, 10, 5, 5 ) ); // start,end,top,bottom
+
+ tet_printf( "Testing with Margin 10,10,5,5\n");
+
+ Stage stage = Stage::GetCurrent();
+
+ auto rootControl = Control::New();
+ auto absoluteLayout = AbsoluteLayout::New();
+ DevelControl::SetLayout( rootControl, absoluteLayout );
+ rootControl.SetName( "AbsoluteLayout" );
+ stage.Add( rootControl );
+
+ auto gridContainer = Control::New();
+ auto gridLayout = Grid::New();
+ gridLayout.SetNumberOfColumns( NUMBER_OF_COLUMNS );
+ gridContainer.SetName( "GridLayout");
+ DevelControl::SetLayout( gridContainer, gridLayout );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::WIDTH_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+ gridContainer.SetProperty( LayoutItem::ChildProperty::HEIGHT_SPECIFICATION, ChildLayoutData::WRAP_CONTENT );
+ gridContainer.SetProperty( Control::Property::PADDING, GRID_PADDING );
+
+ std::vector< Control > controls;
+ for( auto i=0; i < NUMBER_OF_ITEMS; i++ )
+ {
+ auto control = CreateLeafControl( 100, 100 );
+ control.SetProperty(Toolkit::Control::Property::MARGIN, ITEM_MARGIN );
+ controls.push_back( control );
+ }
+
+ for( auto&& iter : controls )
+ {
+ gridContainer.Add( iter );
+ }
+
+ rootControl.Add( gridContainer );
+
+ // Ensure layouting happens
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::POSITION ),
+ Vector3( 0.0f + GRID_PADDING.start + ITEM_MARGIN.start,
+ 0.0f + GRID_PADDING.top + ITEM_MARGIN.top,
+ 0.0f ),
+ 0.0001f, TEST_LOCATION );
+
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::POSITION ),
+ Vector3( 100.0f + GRID_PADDING.start + ITEM_MARGIN.start *2 + ITEM_MARGIN.end,
+ 0.0f + GRID_PADDING.top + ITEM_MARGIN.top,
+ 0.0f ), 0.0001f, TEST_LOCATION );
+
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::POSITION ),
+ Vector3( 0.0f + GRID_PADDING.start + ITEM_MARGIN.start,
+ 100.0f + GRID_PADDING.top + ITEM_MARGIN.top*2 + ITEM_MARGIN.bottom,
+ 0.0f ), 0.0001f, TEST_LOCATION );
+
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::POSITION ),
+ Vector3( 100.0f + GRID_PADDING.start + ITEM_MARGIN.start*2 + ITEM_MARGIN.end,
+ 100.0f + GRID_PADDING.top + ITEM_MARGIN.top*2 + ITEM_MARGIN.bottom,
+ 0.0f ), 0.0001f, TEST_LOCATION );
+
+ tet_infoline(" UtcDaliLayouting_GridLayout03 Size of Grid should include padding and margins");
+
+ const auto NUMBER_OF_ROWS = ( NUMBER_OF_ITEMS / NUMBER_OF_COLUMNS );
+
+ DALI_TEST_EQUALS( gridContainer.GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f * NUMBER_OF_COLUMNS + GRID_PADDING.start + GRID_PADDING.end +
+ ITEM_MARGIN.start *NUMBER_OF_COLUMNS + ITEM_MARGIN.end *NUMBER_OF_COLUMNS,
+ 100.0f * NUMBER_OF_ROWS +
+ GRID_PADDING.top + GRID_PADDING.bottom +
+ ITEM_MARGIN.bottom *NUMBER_OF_ROWS + ITEM_MARGIN.bottom *NUMBER_OF_ROWS,
+ 0.0f ), 0.0001f, TEST_LOCATION );
+
+ tet_infoline(" UtcDaliLayouting_GridLayout03 Item sizes unchanged");
+ DALI_TEST_EQUALS( controls[0].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[1].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[2].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+ DALI_TEST_EQUALS( controls[3].GetProperty<Vector3>( Actor::Property::SIZE ), Vector3( 100.0f, 100.0f, 0.0f ), 0.0001f, TEST_LOCATION );
+
+ END_TEST;
+}
+
+
+int UtcDaliLayouting_GridLayoutDownCast(void)
+{
+ TestApplication application;
+ tet_infoline(" UtcDaliLayouting_GridLayoutDownCast - Testing Downcast");
+
+ Grid gridLayout = Grid::New();
+
+ LayoutGroup layoutGroup( gridLayout );
+
+ Grid gridLayoutCandidate = Grid::DownCast( layoutGroup );
+ DALI_TEST_CHECK( gridLayoutCandidate );
+
+ END_TEST;
+}
\ No newline at end of file
END_TEST;
}
+
+int UtcDaliKeyboardFocusManagerEnableFocusIndicator(void)
+{
+ ToolkitTestApplication application;
+
+ tet_infoline( "Ensure we cannot set an actor to be focused if it is not staged and that we do not retrieve an actor if it has been unstaged" );
+
+ KeyboardFocusManager manager = KeyboardFocusManager::Get();
+ DALI_TEST_CHECK( ! manager.GetCurrentFocusActor() );
+
+ Actor actor = Actor::New();
+ actor.SetKeyboardFocusable( true );
+ Stage::GetCurrent().Add( actor );
+ manager.SetCurrentFocusActor( actor );
+
+ // Press Any key to notice physical keyboard event is comming to KeyboardFocusManager
+ // It makes mIsFocusIndicatorEnabled true and add focus indicator to focused actor.
+ Integration::KeyEvent rightEvent( "Right", "", 0, 0, 0, Integration::KeyEvent::Down, "", DEFAULT_DEVICE_NAME, Device::Class::NONE, Device::Subclass::NONE );
+ application.ProcessEvent(rightEvent);
+
+ Actor indicatorActor = manager.GetFocusIndicatorActor();
+
+ tet_infoline( "Indicator is added to focused actor" );
+ DALI_TEST_CHECK( actor == indicatorActor.GetParent() );
+
+ Dali::Toolkit::DevelKeyboardFocusManager::EnableFocusIndicator(manager, false);
+ DALI_TEST_CHECK( !Dali::Toolkit::DevelKeyboardFocusManager::IsFocusIndicatorEnabled(manager) );
+
+ tet_infoline( "Indicator is removed from focused actor because mUseFocusIndicator is false" );
+ DALI_TEST_CHECK( !indicatorActor.GetParent() );
+
+ END_TEST;
+}
+
+
+
DALI_TEST_EQUALS( label.GetProperty< int >( DevelTextLabel::Property::VERTICAL_LINE_ALIGNMENT ), static_cast< int >( Toolkit::DevelText::VerticalLineAlignment::BOTTOM ), TEST_LOCATION );
END_TEST;
-}
+}
\ No newline at end of file
$(devel_api_src_dir)/layouting/flex-layout.cpp \
$(devel_api_src_dir)/layouting/absolute-layout.cpp \
$(devel_api_src_dir)/layouting/linear-layout.cpp \
+ $(devel_api_src_dir)/layouting/grid.cpp \
$(devel_api_src_dir)/layouting/layout-item.cpp \
$(devel_api_src_dir)/layouting/layout-item-impl.cpp \
$(devel_api_src_dir)/layouting/layout-controller.cpp \
$(devel_api_src_dir)/layouting/absolute-layout.h \
$(devel_api_src_dir)/layouting/child-layout-data.h \
$(devel_api_src_dir)/layouting/flex-layout.h \
+ $(devel_api_src_dir)/layouting/grid.h \
$(devel_api_src_dir)/layouting/linear-layout.h \
$(devel_api_src_dir)/layouting/layout-child-impl.h \
$(devel_api_src_dir)/layouting/layout-controller.h \
GetImpl(keyboardFocusManager).SetCustomAlgorithm(interface);
}
+void EnableFocusIndicator(KeyboardFocusManager keyboardFocusManager, bool enable)
+{
+ GetImpl(keyboardFocusManager).EnableFocusIndicator(enable);
+}
+
+bool IsFocusIndicatorEnabled(KeyboardFocusManager keyboardFocusManager)
+{
+ return GetImpl(keyboardFocusManager).IsFocusIndicatorEnabled();
+}
+
} // namespace DevelKeyboardFocusManager
} // namespace Toolkit
*/
DALI_TOOLKIT_API void SetCustomAlgorithm(KeyboardFocusManager keyboardFocusManager, CustomAlgorithmInterface& interface);
+/**
+ * @brief Decide using focus indicator or not
+ *
+ * @param[in] keyboardFocusManager The instance of KeyboardFocusManager
+ * @param[in] enable Whether using focus indicator or not
+ */
+DALI_TOOLKIT_API void EnableFocusIndicator(KeyboardFocusManager keyboardFocusManager, bool enable);
+
+/**
+ * @brief Check focus indicator is enabled or not
+ *
+ * @param[in] keyboardFocusManager The instance of KeyboardFocusManager
+ * @return True when focus indicator is enabled
+ */
+DALI_TOOLKIT_API bool IsFocusIndicatorEnabled(KeyboardFocusManager keyboardFocusManager);
+
} // namespace DevelKeyboardFocusManager
} // namespace Toolkit
--- /dev/null
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//CLASS HEADER
+#include <dali-toolkit/devel-api/layouting/grid.h>
+
+//EXTERNAL HEADERS
+//INTERNAL HEADERS
+#include <dali-toolkit/internal/layouting/grid-impl.h>
+
+namespace Dali
+{
+namespace Toolkit
+{
+
+Grid::Grid()
+{
+}
+
+Grid Grid::New()
+{
+ Internal::GridPtr internal = Internal::Grid::New();
+ return Grid( internal.Get() );
+}
+
+Grid Grid::DownCast( BaseHandle handle )
+{
+ return Grid( dynamic_cast< Dali::Toolkit::Internal::Grid*>( handle.GetObjectPtr() ) );
+}
+
+Grid::Grid( const Grid& other )
+: LayoutGroup( other )
+{
+}
+
+Grid& Grid::operator=( const Grid& other )
+{
+ if( &other != this )
+ {
+ LayoutGroup::operator=( other );
+ }
+ return *this;
+}
+
+void Grid::SetNumberOfColumns( int columns )
+{
+ GetImplementation(*this).SetNumberOfColumns( columns );
+}
+
+int Grid::GetNumberOfColumns() const
+{
+ return GetImplementation(*this).GetNumberOfColumns();
+}
+
+Grid::Grid( Dali::Toolkit::Internal::Grid* object )
+: LayoutGroup( object )
+{
+}
+
+} // namespace Toolkit
+} // namespace Dali
\ No newline at end of file
--- /dev/null
+#ifndef DALI_TOOLKIT_LAYOUTING_GRID_LAYOUT_H
+#define DALI_TOOLKIT_LAYOUTING_GRID_LAYOUT_H
+
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <dali/public-api/common/dali-common.h>
+#include <dali/public-api/object/base-handle.h>
+#include <dali-toolkit/devel-api/layouting/layout-group.h>
+#include <dali-toolkit/devel-api/layouting/layout-size.h>
+#include <dali-toolkit/public-api/toolkit-property-index-ranges.h>
+
+namespace Dali
+{
+namespace Toolkit
+{
+
+namespace Internal DALI_INTERNAL
+{
+class Grid;
+}
+
+/**
+ * @brief
+ * This class implements a horizontal box layout, automatically handling
+ * right to left or left to right direction change.
+ */
+class DALI_TOOLKIT_API Grid : public LayoutGroup
+{
+public:
+
+ /**
+ * @brief Creates an uninitialized Grid handle.
+ *
+ * Initialize it using Grid::New().
+ * Calling member functions with an uninitialized handle is not allowed.
+ */
+ Grid();
+
+ /**
+ * @brief Creates a Grid object.
+ */
+ static Grid New();
+
+ /**
+ * @brief Downcasts a handle to a Grid handle.
+ *
+ * If handle points to a Grid, the downcast produces a valid handle.
+ * If not, the returned handle is left uninitialized.
+
+ * @param[in] handle to an object
+ * @return Handle to a Grid or an uninitialized handle
+ */
+ static Grid DownCast( BaseHandle handle );
+
+ /**
+ * @brief Copy constructor
+ */
+ Grid( const Grid& other );
+
+ /**
+ * @brief Assigment operator
+ */
+ Grid& operator=( const Grid& other );
+
+ /**
+ * @brief Default destructor.
+ *
+ * This is non-virtual, since derived Handle types must not contain data or virtual methods
+ */
+ ~Grid()=default;
+
+ /**
+ * @brief Set the number of columns in the Grid.
+ * @param[in] columns number of columns,
+ */
+ void SetNumberOfColumns( int columns );
+
+ /**
+ * @brief Get the number of columns in the grid.
+ * @return the number of columns.
+ */
+ int GetNumberOfColumns() const;
+
+public: // Not intended for application developers
+
+ /// @cond internal
+ /**
+ * @brief This constructor is used by Grid::New() methods.
+ *
+ * @param[in] actor A pointer to a newly allocated Dali resource
+ */
+ explicit DALI_INTERNAL Grid( Internal::Grid* body );
+ /// @endcond
+};
+
+} // namespace Toolkit
+} // namespace Dali
+
+#endif // DALI_TOOLKIT_LAYOUTING_GRID_LAYOUT_H
$(toolkit_src_dir)/layouting/flex-layout-impl.cpp \
$(toolkit_src_dir)/layouting/absolute-layout-impl.cpp \
$(toolkit_src_dir)/layouting/linear-layout-impl.cpp \
+ $(toolkit_src_dir)/layouting/grid-locations.cpp \
+ $(toolkit_src_dir)/layouting/grid-impl.cpp \
$(toolkit_src_dir)/layouting/layout-item-data-impl.cpp \
$(toolkit_src_dir)/layouting/layout-group-data-impl.cpp \
$(toolkit_src_dir)/layouting/layout-controller-debug.cpp \
mFocusGroupLoopEnabled( false ),
mIsWaitingKeyboardFocusChangeCommit( false ),
mClearFocusOnTouch( true ),
+ mEnableFocusIndicator( true ),
mFocusHistory(),
mSlotDelegate( this ),
mCustomAlgorithmInterface(NULL)
// Check whether the actor is in the stage and is keyboard focusable.
if( actor && actor.IsKeyboardFocusable() && actor.OnStage() )
{
- if( mIsFocusIndicatorEnabled )
+ if( mIsFocusIndicatorEnabled && mEnableFocusIndicator )
{
actor.Add( GetFocusIndicatorActor() );
}
Actor actor = GetCurrentFocusActor();
if( actor )
{
- // Make sure the focused actor is highlighted
- actor.Add( GetFocusIndicatorActor() );
+ if( mEnableFocusIndicator )
+ {
+ // Make sure the focused actor is highlighted
+ actor.Add( GetFocusIndicatorActor() );
+ }
}
else
{
mCustomAlgorithmInterface = &interface;
}
+void KeyboardFocusManager::EnableFocusIndicator(bool enable)
+{
+ if( !enable && mFocusIndicatorActor )
+ {
+ mFocusIndicatorActor.Unparent();
+ }
+
+ mEnableFocusIndicator = enable;
+}
+
+bool KeyboardFocusManager::IsFocusIndicatorEnabled() const
+{
+ return mEnableFocusIndicator;
+}
+
} // namespace Internal
} // namespace Toolkit
*/
void SetCustomAlgorithm(CustomAlgorithmInterface& interface);
+ /**
+ * @copydoc Toolkit::DevelKeyboardFocusManager::UseFocusIndicator
+ */
+ void EnableFocusIndicator(bool enable);
+
+ /**
+ * @copydoc Toolkit::DevelKeyboardFocusManager::UseFocusIndicator
+ */
+ bool IsFocusIndicatorEnabled() const;
+
public:
/**
bool mClearFocusOnTouch:1; ///< Whether clear focus on touch.
+ bool mEnableFocusIndicator; ///< Whether use focus indicator
+
FocusStack mFocusHistory; ///< Stack to contain pre-focused actor's BaseObject*
SlotDelegate< KeyboardFocusManager > mSlotDelegate;
// EXTERNAL INCLUDES
#include <dali/devel-api/adaptor-framework/image-loading.h>
#include <dali/integration-api/adaptors/adaptor.h>
+#include <dali/devel-api/adaptor-framework/thread-settings.h>
namespace Dali
{
void ImageLoadThread::Run()
{
+ SetThreadName( "ImageLoadThread" );
mLogFactory.InstallLogFunction();
while( LoadingTask* task = NextTaskToProcess() )
--- /dev/null
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//CLASS HEADER
+#include <dali-toolkit/internal/layouting/grid-impl.h>
+
+//EXTERNAL HEADERS
+#include <dali/integration-api/debug.h>
+#include <dali/public-api/common/extents.h>
+#include <dali/public-api/actors/actor.h>
+
+//INTERNAL HEADERS
+#include <dali-toolkit/devel-api/layouting/layout-item.h>
+#include <dali-toolkit/public-api/controls/control-impl.h>
+#include <dali-toolkit/internal/controls/control/control-data-impl.h>
+#include <dali-toolkit/devel-api/layouting/layout-length.h>
+#include <dali-toolkit/internal/layouting/grid-locations.h>
+
+#if defined(DEBUG_ENABLED)
+static Debug::Filter* gLogFilter = Debug::Filter::New( Debug::Concise, false, "LOG_LAYOUT" );
+#endif
+
+namespace Dali
+{
+namespace Toolkit
+{
+namespace Internal
+{
+
+GridPtr Grid::New()
+{
+ GridPtr layout( new Grid() );
+ return layout;
+}
+
+Grid::Grid()
+: LayoutGroup(),
+ mTotalHeight( 0 ),
+ mTotalWidth( 0 ),
+ mNumColumns( AUTO_FIT ),
+ mNumRows( AUTO_FIT ),
+ mRequestedColumnWidth( 0 ),
+ mRequestedNumColumns( AUTO_FIT )
+{
+ mLocations = GridLocations::New();
+}
+
+Grid::~Grid(){}
+
+void Grid::SetNumberOfColumns( int columns )
+{
+ mRequestedNumColumns = columns;
+ // Store value and Relayout if changed.
+ if( columns != mNumColumns )
+ {
+ mNumColumns = columns;
+ RequestLayout();
+ }
+}
+
+int Grid::GetNumberOfColumns() const
+{
+ return mNumColumns;
+}
+
+void Grid::DetermineNumberOfColumns( int availableSpace )
+{
+ if( mRequestedNumColumns == AUTO_FIT )
+ {
+ if( availableSpace > 0 )
+ {
+ // Can only calculate number of columns if a column width has been set
+ mNumColumns = ( mRequestedColumnWidth > 0 ) ? ( availableSpace / mRequestedColumnWidth ) : 1;
+ }
+ }
+}
+
+void Grid::OnMeasure( MeasureSpec widthMeasureSpec, MeasureSpec heightMeasureSpec )
+{
+ DALI_LOG_STREAM( gLogFilter, Debug::Verbose,
+ "Grid::OnMeasure Actor Id:" << Actor::DownCast(GetOwner()).GetId() <<
+ " Owner:" << Actor::DownCast(GetOwner()).GetName() <<
+ " MeasureSpecs( width:"<<widthMeasureSpec<<", height:"<<heightMeasureSpec );
+
+ auto gridWidthMode = widthMeasureSpec.GetMode();
+ auto gridHeightMode = heightMeasureSpec.GetMode();
+ LayoutLength widthSize = widthMeasureSpec.GetSize();
+ LayoutLength heightSize = heightMeasureSpec.GetSize();
+
+ int availableContentWidth(0);
+ int availableContentHeight(0);
+
+ LayoutLength desiredChildHeight( 0 );
+ LayoutLength desiredChildWidth( 0 );
+
+ Extents gridLayoutPadding = GetPadding();
+
+ auto childCount = GetChildCount();
+
+ // WIDTH SPECIFICATIONS
+
+ // measure first child and use it's dimensions for layout measurement
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Grid::OnMeasure MeasureSpec::Mode::EXACTLY or MeasureSpec::Mode::AT_MOST \n" );
+
+ if( childCount > 0 )
+ {
+ auto childLayoutItem = GetChildAt( 0 );
+ if( childLayoutItem )
+ {
+ auto childOwner = childLayoutItem->GetOwner();
+
+ MeasureChild( childLayoutItem, widthMeasureSpec, heightMeasureSpec );
+ desiredChildHeight = childLayoutItem->GetMeasuredHeight();
+ desiredChildWidth = childLayoutItem->GetMeasuredWidth();
+
+ // If child has a margin then add it to desired size
+ Extents childMargin = childOwner.GetProperty<Extents>( Toolkit::Control::Property::MARGIN );
+ desiredChildHeight += childMargin.top + childMargin.bottom;
+ desiredChildWidth += childMargin.start + childMargin.end;
+
+ mTotalWidth = desiredChildWidth * mNumColumns;
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Grid::OnMeasure TotalDesiredWidth(%d) \n", mTotalWidth.mValue );
+ } // Child is LayoutItem
+ } // Child exists
+
+ // Include padding for max and min checks
+ mTotalWidth += gridLayoutPadding.start + gridLayoutPadding.end;
+
+ // Ensure width does not exceed specified atmost width or less than mininum width
+ mTotalWidth = std::max( mTotalWidth, GetSuggestedMinimumWidth() );
+
+ // widthMode EXACTLY so grid must be the given width
+ if( gridWidthMode == MeasureSpec::Mode::EXACTLY || gridWidthMode == MeasureSpec::Mode::AT_MOST )
+ {
+ // In the case of AT_MOST, widthSize is the max limit.
+ mTotalWidth = std::min( mTotalWidth, widthSize );
+ }
+
+ availableContentWidth = mTotalWidth - gridLayoutPadding.start - gridLayoutPadding.end;
+ widthSize = mTotalWidth;
+
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Grid::OnMeasure availableContentWidth(%d) mTotalWidth(%d) \n",
+ availableContentWidth,
+ mTotalWidth.mValue );
+ // HEIGHT SPECIFICATIONS
+
+ // heightMode EXACTLY so grid must be the given height
+ if( gridHeightMode == MeasureSpec::Mode::EXACTLY || gridHeightMode == MeasureSpec::Mode::AT_MOST )
+ {
+ if( childCount > 0 )
+ {
+ mTotalHeight = gridLayoutPadding.top + gridLayoutPadding.bottom;
+
+ for( auto i = 0u; i < childCount; i += mNumColumns )
+ {
+ mTotalHeight += desiredChildHeight;
+ }
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Grid::OnMeasure TotalDesiredHeight(%d) \n",
+ mTotalHeight.mValue );
+
+ // Ensure ourHeight does not exceed specified atmost height
+ mTotalHeight = std::min( mTotalHeight, heightSize );
+ mTotalHeight = std::max( mTotalHeight, GetSuggestedMinimumHeight() );
+
+ heightSize = mTotalHeight;
+ } // Child exists
+
+ // In the case of AT_MOST, availableContentHeigth is the max limit.
+ availableContentHeight = heightSize - gridLayoutPadding.top - gridLayoutPadding.bottom;
+ }
+ else
+ {
+ // Grid expands to fit content
+
+ // If number of columns AUTO_FIT then set to 1 column.
+
+ // Calculate numbers of rows, round down result as later check for remainder.
+ mNumRows = childCount / ( ( mNumColumns ) ? mNumColumns : 1 );
+ // If number of cells not cleanly dividable by colums, add another row to house remainder cells.
+ mNumRows += ( childCount % ( ( mNumColumns ) ? mNumColumns : 1 ) ) ? 1 : 0;
+
+ availableContentHeight = desiredChildHeight * mNumRows;
+ }
+
+ // If number of columns not defined
+ DetermineNumberOfColumns( availableContentWidth );
+
+ // Locations define the start, end,top and bottom of each cell.
+ mLocations->CalculateLocations( mNumColumns, availableContentWidth, availableContentHeight, childCount, 0, 0 );
+
+
+ SetMeasuredDimensions( ResolveSizeAndState( widthSize, widthMeasureSpec, MeasuredSize::State::MEASURED_SIZE_OK ),
+ ResolveSizeAndState( heightSize, heightMeasureSpec, MeasuredSize::State::MEASURED_SIZE_OK ) );
+}
+
+void Grid::OnLayout( bool changed, LayoutLength left, LayoutLength top, LayoutLength right, LayoutLength bottom )
+{
+ auto owner = GetOwner();
+ auto actor = Actor::DownCast(owner);
+ auto count = GetChildCount();
+
+ GridLocations::LocationVector locations = mLocations->GetLocations();
+
+ Extents gridLayoutPadding = GetPadding();
+ Extents childMargins;
+
+ // Margin for all children dependant on if set on first child
+ if( count )
+ {
+ LayoutItemPtr childLayout = GetChildAt( 0 );
+ if( childLayout )
+ {
+ auto childOwner = childLayout->GetOwner();
+ if( childOwner )
+ {
+ childMargins = childOwner.GetProperty<Extents>( Toolkit::Control::Property::MARGIN );
+ }
+ }
+ }
+
+ for( unsigned int i = 0; i < count; i++)
+ {
+ // for each child
+ int childIndex = i;
+ LayoutItemPtr childLayout = GetChildAt( childIndex );
+ if( childLayout != nullptr )
+ {
+ // Get start and end position of child x1,x2
+ auto x1 = locations[ i ].xStart;
+ auto x2 = locations[ i ].xEnd;
+
+ // Get top and bottom position of child y1,y2
+ auto y1 = locations[ i ].yTop;
+ auto y2 = locations[ i ].yBottom;
+
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Grid::OnLayout cellSize(%d,%d) \n", x2 - x1, y2 - y1);
+
+ // Offset children by the grids padding if present
+ x1 += gridLayoutPadding.start;
+ x2 += gridLayoutPadding.start;
+ y1 += gridLayoutPadding.top;
+ y2 += gridLayoutPadding.top;
+
+ // Offset children by the margin of the first child ( if required ).
+ x1 += childMargins.start;
+ x2 -= childMargins.end;
+ y1 += childMargins.top;
+ y2 -= childMargins.bottom;
+
+ childLayout->Layout( x1, y1, x2, y2 );
+ }
+ }
+}
+
+} // namespace Internal
+} // namespace Toolkit
+} // namespace Dali
--- /dev/null
+#ifndef DALI_TOOLKIT_INTERNAL_LAYOUTING_GRID_IMPL_H
+#define DALI_TOOLKIT_INTERNAL_LAYOUTING_GRID_IMPL_H
+
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// EXTERNAL_HEADERS
+#include <dali/public-api/common/intrusive-ptr.h>
+#include <dali/public-api/object/base-object.h>
+
+// INTERNAL_HEADERS
+#include <dali-toolkit/devel-api/layouting/layout-group-impl.h>
+#include <dali-toolkit/devel-api/layouting/grid.h>
+#include <dali-toolkit/internal/layouting/grid-locations.h>
+
+namespace Dali
+{
+namespace Toolkit
+{
+namespace Internal
+{
+
+class Grid;
+using GridPtr = IntrusivePtr<Grid>;
+
+class Grid final : public LayoutGroup
+{
+public:
+
+ /**
+ * Creates a pointer to an Internal Grid
+ */
+ static GridPtr New();
+
+ /**
+ * Set grid's the number of columns
+ * @param[in] columns number of columns
+ */
+ void SetNumberOfColumns( int columns );
+
+ /**
+ * Get number of columns, -1 would indicate AUTO_FIT
+ * which means the number has not been set but will be calculated.
+ * @return the number of columns set
+ */
+ int GetNumberOfColumns() const;
+
+ // Movable but not copyable
+ Grid( const Grid& other ) = delete;
+ Grid& operator=( const Grid& other ) = delete;
+ Grid( Grid && ) = default;
+ Grid& operator=( Grid && ) = default;
+
+protected:
+
+ /**
+ * Default Constructor
+ */
+ Grid();
+
+ /**
+ * Destructor
+ */
+ ~Grid();
+
+ /**
+ * @copydoc LayoutItem::OnMeasure
+ */
+ virtual void OnMeasure( MeasureSpec widthMeasureSpec, MeasureSpec heightMeasureSpec ) override;
+
+ /**
+ * @copydoc LayoutItem::OnLayout
+ */
+ virtual void OnLayout( bool changed, LayoutLength l, LayoutLength t, LayoutLength r, LayoutLength b ) override;
+
+private:
+
+ /**
+ * @brief
+ * For the given availableSpace, calculate or retreive the number of required columns.
+ * @param[in] availableSpace the space available for a child in each column.
+ */
+ void DetermineNumberOfColumns( int availableSpace );
+
+private:
+
+ GridLocationsPtr mLocations;
+
+ LayoutLength mTotalHeight;
+ LayoutLength mTotalWidth;
+
+ const int AUTO_FIT = -1;
+
+ int mNumColumns;
+ int mNumRows;
+
+ int mHorizontalSpacing = 0;
+ int mVerticalSpacing = 0;
+ int mRequestedHorizontalSpacing;
+ int mRequestedColumnWidth;
+ int mRequestedNumColumns;
+ int mRequestedNumRows;
+};
+
+} // namespace Internal
+
+inline Internal::Grid& GetImplementation( Dali::Toolkit::Grid& handle )
+{
+ DALI_ASSERT_ALWAYS( handle && "Grid handle is empty" );
+ BaseObject& object = handle.GetBaseObject();
+ return static_cast<Internal::Grid&>( object );
+}
+
+inline const Internal::Grid& GetImplementation( const Dali::Toolkit::Grid& handle )
+{
+ DALI_ASSERT_ALWAYS( handle && "Grid handle is empty" );
+ const BaseObject& object = handle.GetBaseObject();
+ return static_cast<const Internal::Grid&>( object );
+}
+
+} // namespace Toolkit
+} // namespace Dali
+
+#endif // DALI_TOOLKIT_INTERNAL_LAYOUTINGInner
\ No newline at end of file
--- /dev/null
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//CLASS HEADER
+#include <dali-toolkit/internal/layouting/grid-locations.h>
+
+// EXTERNAL HEADERS
+#include <dali/integration-api/debug.h>
+
+// INTERNAL HEADERS
+#include <dali-toolkit/devel-api/layouting/layout-item.h>
+
+namespace
+{
+
+#if defined(DEBUG_ENABLED)
+static Debug::Filter* gLogFilter = Debug::Filter::New( Debug::Concise, false, "LOG_AXIS" );
+#endif
+
+}
+
+namespace Dali
+{
+namespace Toolkit
+{
+namespace Internal
+{
+
+GridLocationsPtr GridLocations::New()
+{
+ GridLocationsPtr gridAxis( new GridLocations() );
+ return gridAxis;
+}
+
+GridLocations::GridLocations()
+: mLocations()
+{
+}
+
+GridLocations::~GridLocations(){}
+
+void GridLocations::CalculateLocations( int numberOfColumns,
+ unsigned int availableWidth,
+ unsigned int availableHeight,
+ unsigned int numberOfCells,
+ unsigned int columnWidth,
+ unsigned int rowHeight )
+{
+ mLocations.clear();
+
+ // Calculate width and height of columns and rows.
+
+ // Calculate numbers of rows, round down result as later check for remainder.
+ unsigned int numberOfRows = numberOfCells/numberOfColumns;
+ // If number of cells not cleanly dividable by colums, add another row to house remainder cells.
+ numberOfRows += (numberOfCells%numberOfColumns)?1:0;
+
+ unsigned int maxColumnWidth = availableWidth / numberOfColumns;
+
+ if( columnWidth > 0 )
+ {
+ // Column width supplied so use this unless exceeds available width.
+ columnWidth = std::min( columnWidth, maxColumnWidth );
+ }
+ else
+ {
+ // Column width not supplied so use calculated value
+ columnWidth = maxColumnWidth;
+ }
+
+ unsigned int maxRowHeight = availableHeight / numberOfRows;
+
+ if( rowHeight > 0 )
+ {
+ // Column height supplied so use this unless exceeds available height.
+ rowHeight = std::min( rowHeight, maxRowHeight );
+ }
+ else
+ {
+ // Column height not supplied so use calculated value
+ rowHeight = maxRowHeight;
+ }
+
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "ColumWidth[%d] RowHeight[%d] NumberOfRows[%d] NumberOfColumns[%d]\n",
+ columnWidth, rowHeight, numberOfRows, numberOfColumns );
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Remainder[%d]\n", numberOfCells%numberOfColumns );
+
+ int y1 = 0;
+ int y2 = y1 + rowHeight;
+
+ // Calculate start, end, top and bottom coordinate of each cell.
+
+ // Iterate rows
+ for( auto i = 0u; i < numberOfRows; i++ )
+ {
+ int x1 = 0;
+ int x2 = x1 + columnWidth;
+
+ // Iterate columns
+ for( auto j = 0; j < numberOfColumns; j++ )
+ {
+ GridLocations::Cell cell( x1, x2, y1, y2 );
+ mLocations.push_back( cell );
+ // Calculate starting x and ending x position of each column
+ x1 = x2;
+ x2 = x2 + columnWidth;
+ }
+
+ // Calculate top y and bottom y position of each row.
+ y1 = y2;
+ y2 = y2 + rowHeight;
+ }
+
+#if defined(DEBUG_ENABLED)
+ std::ostringstream oss;
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "GridLocations::CalculateLocations (%d)\n", numberOfCells );
+ for( auto i = 0u; i < numberOfCells; i++ )
+ {
+ DALI_LOG_STREAM( gLogFilter, Debug::Verbose,"x1:"<<mLocations[i].xStart<<" x2:"<<mLocations[i].xEnd<<" y1:"<<mLocations[i].yTop<<" y2:"<<mLocations[i].yBottom);
+ }
+#endif
+}
+
+GridLocations::LocationVector GridLocations::GetLocations()
+{
+#if defined(DEBUG_ENABLED)
+ std::ostringstream oss;
+ auto itemCount = mLocations.size(); // mVerticalLocations mirrors this so same size.
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "GridLocations::GetLocations for %u cells\n", itemCount );
+ for( auto i = 0u; i < itemCount; i++ )
+ {
+ DALI_LOG_STREAM( gLogFilter, Debug::Verbose,"x1:"<<mLocations[i].xStart<<" x2:"<<mLocations[i].xEnd<<" y1:"<<mLocations[i].yTop<<" y2:"<<mLocations[i].yBottom);
+ }
+#endif
+
+ return mLocations;
+}
+
+} // namespace Internal
+
+} // namespace Toolkit
+} // namespace Dali
\ No newline at end of file
--- /dev/null
+#ifndef DALI_TOOLKIT_INTERNAL_LAYOUTING_GRID_LOCATIONS_H
+#define DALI_TOOLKIT_INTERNAL_LAYOUTING_GRID_LOCATIONS_H
+
+/*
+ * Copyright (c) 2018 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//EXTERNAL HEADERS
+#include <dali/public-api/common/intrusive-ptr.h>
+#include <dali/public-api/common/dali-vector.h>
+#include <dali/public-api/object/ref-object.h>
+#include <limits.h>
+
+// INTERNAL HEADERS
+#include <dali-toolkit/devel-api/layouting/layout-item-impl.h>
+
+namespace Dali
+{
+namespace Toolkit
+{
+namespace Internal
+{
+
+class GridLocations;
+using GridLocationsPtr = IntrusivePtr<GridLocations>;
+
+/* @brief This internal class houses the algorithm for computing the locations and size of cells.
+ *
+ * A Grid layout uses two instances of this class
+ * distinguished by the "horizontal" flag which is true for the horizontal axis and false
+ * for the vertical one.
+ */
+
+class GridLocations : public RefObject
+{
+
+public:
+
+ static const int UNDEFINED = INT_MIN;
+
+ static const unsigned int HORIZONTAL = 0;
+ static const unsigned int VERTICAL = 1;
+
+ struct Cell
+ {
+ int xStart;
+ int xEnd;
+ int yTop;
+ int yBottom;
+ int explictlyDefined;
+
+ Cell( int x1, int x2, int y1, int y2): xStart(x1), xEnd(x2), yTop(y1), yBottom(y2){};
+ };
+
+ typedef std::vector< Cell > LocationVector;
+
+public:
+
+ static GridLocationsPtr New();
+
+ /*
+ * Uses the given parameters to calculate the x,y coordinates of each cell and cell size.
+ */
+ void CalculateLocations( int numberOfColumns, unsigned int availableWidth,
+ unsigned int availableHeight, unsigned int numberOfCells,
+ unsigned int columnWidth, unsigned int rowHeight );
+
+ LocationVector GetLocations();
+
+private:
+
+ GridLocations();
+ ~GridLocations();
+ GridLocations( const GridLocations& other ) = delete;
+ GridLocations& operator=( const GridLocations& other ) = delete;
+
+private:
+
+ LocationVector mLocations;
+
+};
+
+} // namespace Internal
+} // namespace Toolkit
+} // namespace Dali
+
+#endif // DALI_TOOLKIT_INTERNAL_LAYOUTING_GRID_LOCATIONS_H
\ No newline at end of file
*
*/
+// EXTERNAL INCLUDES
+#include <dali/devel-api/text-abstraction/font-list.h>
+
// INTERNAL INCLUDES
#include <dali-toolkit/internal/text/character-run.h>
*/
struct FontRun
{
- CharacterRun characterRun; ///< The initial character index and the number of characters of the run.
- FontId fontId; ///< Font id of the run.
+ CharacterRun characterRun; ///< The initial character index and the number of characters of the run.
+ FontId fontId; ///< Font id of the run.
+ bool softwareItalic:1; ///< Whether font needs software support to draw italic style
+ bool softwareBold:1; ///< Whether font needs software support to draw bold style
};
} // namespace Text
FontId previousFontId = 0u;
bool isPreviousEmojiScript = false;
+ // Description of fallback font which is selected at current iteration.
+ TextAbstraction::FontDescription selectedFontDescription;
+
CharacterIndex lastCharacter = startIndex + numberOfCharacters;
for( Length index = startIndex; index < lastCharacter; ++index )
{
// Get the current character.
const Character character = *( textBuffer + index );
+ bool needSoftwareBoldening = false;
+ bool needSoftwareItalic = false;
+ // new description for current character
TextAbstraction::FontDescription currentFontDescription;
TextAbstraction::PointSize26Dot6 currentFontPointSize = defaultFontPointSize;
bool isDefaultFont = true;
}
#endif
+ if( fontId != currentFontRun.fontId )
+ {
+ fontClient.GetDescription(fontId,selectedFontDescription);
+ }
+
+ // Developer sets bold to character but selected font cannot support it
+ needSoftwareBoldening = ( currentFontDescription.weight >= TextAbstraction::FontWeight::BOLD ) && ( selectedFontDescription.weight < TextAbstraction::FontWeight::BOLD );
+
+ // Developer sets italic to character but selected font cannot support it
+ needSoftwareItalic = ( currentFontDescription.slant == TextAbstraction::FontSlant::ITALIC ) && ( selectedFontDescription.slant < TextAbstraction::FontSlant::ITALIC );
+
// The font is now validated.
if( ( fontId != currentFontRun.fontId ) ||
- isNewParagraphCharacter )
+ isNewParagraphCharacter ||
+ // If font id is same as previous but style is diffrent, initialize new one
+ ( ( fontId == currentFontRun.fontId ) && ( ( needSoftwareBoldening != currentFontRun.softwareBold ) || ( needSoftwareItalic != currentFontRun.softwareItalic ) ) ) )
{
// Current run needs to be stored and a new one initialized.
currentFontRun.characterRun.characterIndex = currentFontRun.characterRun.characterIndex + currentFontRun.characterRun.numberOfCharacters;
currentFontRun.characterRun.numberOfCharacters = 0u;
currentFontRun.fontId = fontId;
+ currentFontRun.softwareItalic = needSoftwareItalic;
+ currentFontRun.softwareBold = needSoftwareBoldening;
}
// Add one more character to the run.
mFontClient.CreateBitmap( glyph.fontId,
glyph.index,
+ glyph.softwareItalic,
+ glyph.softwareBold,
glyphBufferData,
outline );
{
fontClient.CreateBitmap( glyphInfo->fontId,
glyphInfo->index,
+ glyphInfo->softwareItalic,
+ glyphInfo->softwareBold,
glyphData.glyphBitmap,
outlineWidth );
}
currentFontId = fontRun.fontId;
currentScript = scriptRun.script;
+ bool softwareItalic = fontRun.softwareItalic;
+ bool softwareBold = fontRun.softwareBold;
// Get the min index to the last character of both runs.
CharacterIndex currentIndex = min( fontRun.characterRun.characterIndex + fontRun.characterRun.numberOfCharacters,
// Retrieve the glyphs and the glyph to character conversion map.
Vector<GlyphInfo> tmpGlyphs;
Vector<CharacterIndex> tmpGlyphToCharacterMap;
- tmpGlyphs.Resize( numberOfGlyphs );
+
+ GlyphInfo glyphInfo;
+ glyphInfo.softwareItalic = softwareItalic;
+ glyphInfo.softwareBold = softwareBold;
+
+ tmpGlyphs.Resize( numberOfGlyphs, glyphInfo );
tmpGlyphToCharacterMap.Resize( numberOfGlyphs );
shaping.GetGlyphs( tmpGlyphs.Begin(),
tmpGlyphToCharacterMap.Begin() );
// INTERNAL INCLUDES
#include <dali-toolkit/third-party/nanosvg/nanosvgrast.h>
#include <dali-toolkit/internal/visuals/svg/svg-visual.h>
+#include <dali/devel-api/adaptor-framework/thread-settings.h>
namespace Dali
{
void SvgRasterizeThread::Run()
{
+ SetThreadName( "SVGThread" );
while( RasterizingTaskPtr task = NextTaskToProcess() )
{
task->Rasterize( mRasterizer );
const unsigned int TOOLKIT_MAJOR_VERSION = 1;
const unsigned int TOOLKIT_MINOR_VERSION = 3;
-const unsigned int TOOLKIT_MICRO_VERSION = 35;
+const unsigned int TOOLKIT_MICRO_VERSION = 36;
const char * const TOOLKIT_BUILD_DATE = __DATE__ " " __TIME__;
#ifdef DEBUG_ENABLED
Name: dali-toolkit
Summary: Dali 3D engine Toolkit
-Version: 1.3.35
+Version: 1.3.36
Release: 1
Group: System/Libraries
License: Apache-2.0 and BSD-3-Clause and MIT