Executing the tests
-------------------
+To see a list of all of the options:
+
+ ./execute.sh -h
+
To execute tests, cd into automated-tests and run
./execute.sh
This will execute dali and dali-internal test sets. Note that the output summary for the first will be printed before running the second.
-By default the tests execute in parallel, which is faster but does not produce any test case output. Use this to execute the tests in series:
+By default the tests execute in parallel, which is faster but does not produce any test case output files. Use this to execute the tests in series and log test output to stdout/err
- ./execute.sh -s
+ ./execute.sh -S
-To see the results, copy the style folder from web-tct_2.2.1_r1/tools/tct-mgr/style into automated-tests and run
+To use test kit lite, (which is very slow),
- firefox --new-window summary.xml
+ ./execute.sh -s
-To see a list of all of the options:
+To see the test kit lite results, copy the style folder from web-tct_2.2.1_r1/tools/tct-mgr/style into automated-tests and run
- ./execute.sh -h
+ firefox --new-window summary.xml
To execute a subset of tests, you can run individual test sets, e.g.
- ./execute.sh dali
+ ./execute.sh dali-toolkit
-To get coverage output, run
+To get coverage output (you need to first build dali libraries with
+--coverage), run
./coverage.sh
On desktop, you can debug the tests by running gdb on the test program:
$ cd automated-tests
- $ gdb build/src/dali/tct-dali-core
+ $ gdb build/src/dali-toolkit/tct-dali-toolkit-core
gdb> r <TestCase>
replace `<TestCase>` with the name of the failing testcase.
-For example, using testcase UtcDaliNinePatch01 from the dali-core test suite:
+For example, using testcase UtcDaliControlBackgroundProperties from the dali-toolkit test suite:
- $ gdb build/src/dali/tct-dali-core
- gdb> r UtcDaliNinePatch01
+ $ gdb build/src/dali-toolkit/tct-dali-toolkit-core
+ gdb> r UtcDaliControlBackgroundProperties
On target, you can re-install the test RPM and associated debug RPMs manually using
After installing the rpm and it's debug RPMs, you can find the executable in /opt/usr/bin/tct-dali-core. First ensure you have smack permissions set:
chsmack -e "^" /usr/bin/gdb
- chsmack -e "^" /opt/usr/bin/tct-dali-core/tct-dali-core
+ chsmack -e "^" /opt/usr/bin/tct-dali-toolkit-core/tct-dali-toolkit-core
then run it under gdb as above.
fi
done
fi
+
+echo "Build succeeded"
+exit 0
#!/bin/bash
-TEMP=`getopt -o hsr --long help,serial,rerun -n 'execute.sh' -- "$@"`
+TEMP=`getopt -o hsSm --long help,serial,tct,modules -n 'execute.sh' -- "$@"`
if [ $? != 0 ] ; then echo "Terminating..." >&2 ; exit 1 ; fi
function usage
{
- echo -e "Usage: execute.sh\t\tExecute test cases from all modules in parallel"
- echo -e " execute.sh <testmodule>\tExecute test cases from the given module in parallel"
- echo -e " execute.sh -s\t\tExecute test cases in serial using Testkit-Lite"
- echo -e " execute.sh -r\t\tExecute test cases in parallel, re-running failed test cases in serial afterwards"
+ echo -e "Usage: execute.sh [-s|-S|-r] [module|testcase]"
+ echo -e " execute.sh\t\tExecute test cases from all modules in parallel"
+ echo -e " execute.sh [module]\tExecute test cases from the given module in parallel"
+ echo -e " execute.sh -s [module]\t\tExecute test cases in serial using Testkit-Lite"
+ echo -e " execute.sh -S [module]\t\tExecute test cases in serial"
echo -e " execute.sh <testcase>\tFind and execute the given test case"
exit 2
}
-opt_serial=0
-opt_rerun=""
+opt_tct=0
+opt_serial=""
+opt_modules=0
while true ; do
case "$1" in
-h|--help) usage ;;
- -s|--serial) opt_serial=1 ; shift ;;
- -r|--rerun) opt_rerun="-r" ; shift ;;
+ -s|--tct) opt_tct=1 ; shift ;;
+ -S|--serial) opt_serial="-s" ; shift ;;
+ -m|--modules) opt_modules=1 ; shift ;;
--) shift; break;;
*) echo "Internal error $1!" ; exit 1 ;;
esac
done
-function execute
+function execute_tct
{
scripts/tctestsgen.sh $1 `pwd` desktop $2
testkit-lite -f `pwd`/tests.xml -o tct-${1}-core-tests.xml -A --comm localhost
scripts/add_style.pl $1
}
+function summary_start
+{
+ start=`date +"%Y-%m-%d_%H_%M_%S"`
+ cat > summary.xml <<EOF
+<?xml version="1.0" encoding="UTF-8"?>
+<?xml-stylesheet type="text/xsl" href="./style/summary.xsl"?>
+<result_summary plan_name="Core">
+ <other xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="xs:string" />
+ <summary test_plan_name="Dali">
+ <start_at>$start</start_at>
+ <end_at>$start</end_at>
+ </summary>
+EOF
+}
+
+function summary_end
+{
+ cat >> summary.xml <<EOF
+</result_summary>
+EOF
+}
+if [ $opt_modules == 1 ] ; then
+ modules= get_modules
+ echo $modules
+ exit 0
+fi
# Clean up old test results
rm -f tct*core-tests.xml
# Clean up old coverage data
if [ -d ../build/tizen ] ; then
- rm -f ../build/tizen/dali-core/.libs/*.gcda
+ rm -f ../build/tizen/dali-toolkit/.libs/*.gcda
fi
find build \( -name "*.gcda" \) -exec rm '{}' \;
ASCII_BOLD="\e[1m"
ASCII_RESET="\e[0m"
-if [ $opt_serial = 1 ] ; then
+modules=`ls -1 src/ | grep -v CMakeList | grep -v common | grep -v manual`
+if [ -f summary.xml ] ; then unlink summary.xml ; fi
+
+if [ $opt_tct == 1 ] ; then
+ # Use Test-kit lite
# Run all test case executables serially, create XML output
if [ -n "$1" ] ; then
- execute $1 $*
+ execute_tct $1 $*
else
- for mod in `ls -1 src/ | grep -v CMakeList `
+ for mod in $modules
do
if [ $mod != 'common' ] && [ $mod != 'manual' ]; then
echo -ne "$ASCII_BOLD"
echo -e "Executing $mod$ASCII_RESET"
- execute $mod $*
+ execute_tct $mod $*
fi
done
fi
scripts/summarize.pl
+
else
- # if $1 is an executable filename, execute it·
+ # Execute test cases using own test harness
if [ -z "$1" ] ; then
# No arguments:
- # Execute each test executable in turn, using parallel execution
- for mod in `ls -1 src/ | grep -v CMakeList | grep -v common | grep -v manual`
+ # Execute each test executable in turn (by default, runs tests in parallel)
+ summary_start
+ for mod in $modules
do
echo -e "$ASCII_BOLD"
echo -e "Executing $mod$ASCII_RESET"
- build/src/$mod/tct-$mod-core $opt_rerun
+ build/src/$mod/tct-$mod-core -r $opt_serial
done
+ summary_end
elif [ -f "build/src/$1/tct-$1-core" ] ; then
# First argument is an executable filename - execute only that with any
# remaining arguments
+ summary_start
module=$1
shift;
- build/src/$module/tct-$module-core $opt_rerun $*
+ build/src/$module/tct-$module-core -r $opt_serial $*
+ summary_end
else
# First argument is not an executable. Is it a test case name?
# Try executing each executable with the test case name until success/known failure
- for mod in `ls -1 src/ | grep -v CMakeList | grep -v common | grep -v manual`
+ for mod in $modules
do
output=`build/src/$mod/tct-$mod-core $1`
ret=$?
echo $1 not found
fi
fi
+
+if [ -f summary.xml ] ; then
+ scripts/output_summary.pl
+fi
+
+exit $?
--- /dev/null
+#!/usr/bin/perl
+
+# Reads summary.xml and produces human readable output
+
+use strict;
+use XML::Parser;
+use Encode;
+use Getopt::Long;
+use Cwd;
+
+my $pwd = getcwd;
+my $text = "";
+my $module="";
+my %modules=();
+
+sub handle_start
+{
+ my ($p, $elt, %attrs) = @_;
+
+ if($elt =~ /suite/)
+ {
+ $module=$attrs{"name"};
+ }
+ if($elt =~ /_case/)
+ {
+ $text = "";
+ }
+}
+
+sub handle_end
+{
+ my ($p, $elt) = @_;
+ if($elt =~ /pass_case/)
+ {
+ $modules{$module}->{"pass"}=$text;
+ $text="";
+ }
+ elsif($elt =~ /fail_case/)
+ {
+ $modules{$module}->{"fail"}=$text;
+ $text="";
+ }
+}
+
+sub handle_char
+{
+ my ($p, $str) = @_;
+ $text .= $str;
+}
+
+my($parser) = new XML::Parser(Handlers => {Start => \&handle_start,
+ End => \&handle_end,
+ Char => \&handle_char});
+$parser->parsefile("summary.xml");
+
+my $RED_COLOR="\e[1;31m";
+my $GREEN_COLOR="\e[1;32m";
+my $ASCII_RESET="\e[0m";
+my $ASCII_BOLD="\e[1m";
+
+print "\n";
+my $totalFailures=0;
+foreach $module (keys(%modules))
+{
+ my $result_colour = $GREEN_COLOR;
+ if( $modules{$module}->{"fail"} )
+ {
+ $result_colour = $RED_COLOR;
+ }
+ my $numPasses = $modules{$module}->{"pass"};
+ my $numFailures = $modules{$module}->{"fail"};
+ $totalFailures += $numFailures;
+ print( "$ASCII_BOLD$module results:$ASCII_RESET\n" );
+ printf("Number of test passes: %s%4d (%5.2f%%)%s\n", $ASCII_BOLD, $numPasses, 100.0 * $numPasses / ($numPasses+$numFailures), $ASCII_RESET);
+ printf("%sNumber of test failures:%s %s%4d%s\n\n", $result_colour, $ASCII_RESET, $ASCII_BOLD, $numFailures, $ASCII_RESET);
+}
+
+exit $totalFailures == 0;
#!/usr/bin/perl
+# Generates an XML summary of test cases from Test-kit lite output XML.
+
use strict;
use XML::Parser;
use Encode;
PKG_CHECK_MODULES(${CAPI_LIB} REQUIRED
dali-core
- dali
+ dali-adaptor
dali-toolkit
)
{
int result = TestHarness::EXIT_STATUS_BAD_ARGUMENT;
- const char* optString = "r";
- bool optRerunFailed(false);
+ const char* optString = "rs";
+ bool optRerunFailed(true);
+ bool optRunSerially(false);
int nextOpt = 0;
do
case 'r':
optRerunFailed = true;
break;
+ case 's':
+ optRunSerially = true;
+ break;
case '?':
TestHarness::Usage(argv[0]);
exit(TestHarness::EXIT_STATUS_BAD_ARGUMENT);
if( optind == argc ) // no testcase name in argument list
{
- result = TestHarness::RunAllInParallel(argv[0], tc_array, optRerunFailed);
+ if( optRunSerially )
+ {
+ result = TestHarness::RunAll( argv[0], tc_array );
+ }
+ else
+ {
+ result = TestHarness::RunAllInParallel( argv[0], tc_array, optRerunFailed );
+ }
}
else
{
tet_infoline(" UtcDaliTextCharacterSetConversionGetNumberOfUtf8Bytes");
unsigned int utf32_01[] = { 0x48, 0x65, 0x6C, 0x6C, 0x6F, 0x20, 0x57, 0x6F, 0x72, 0x6C, 0x64 }; // Hello World
- unsigned int utf32_02[] = { 0x645, 0x631, 0x62D, 0x628, 0x627, 0x20, 0x628, 0x627, 0x644, 0x639, 0x627, 0x644, 0x645 }; // مرحبا بالعالم
- unsigned int utf32_03[] = { 0x939, 0x948, 0x932, 0x94B, 0x20, 0x935, 0x930, 0x94D, 0x932, 0x94D, 0x921 }; // हैलो वर्ल्ड
- unsigned int utf32_04[] = { 0x1F601, 0x20, 0x1F602, 0x20, 0x1F603, 0x20, 0x1F604 }; // Emojis
+ unsigned int utf32_02[] = { 0xA, 0x20, 0x48, 0x65, 0x6C, 0x6C, 0x6F, 0xA, 0x20, 0x57, 0x6F, 0x72, 0x6C, 0x64 }; // Hello World + CR and CR+LF
+ unsigned int utf32_03[] = { 0x645, 0x631, 0x62D, 0x628, 0x627, 0x20, 0x628, 0x627, 0x644, 0x639, 0x627, 0x644, 0x645 }; // مرحبا بالعالم
+ unsigned int utf32_04[] = { 0x939, 0x948, 0x932, 0x94B, 0x20, 0x935, 0x930, 0x94D, 0x932, 0x94D, 0x921 }; // हैलो वर्ल्ड
+ unsigned int utf32_05[] = { 0x1F601, 0x20, 0x1F602, 0x20, 0x1F603, 0x20, 0x1F604 }; // Emojis
const Utf8ToUtf32Data data[] =
{
utf32_01,
},
{
+ "Latin script with 'CR' and 'CR'+'LF'",
+ "\xd Hello\xd\xa World",
+ utf32_02,
+ },
+ {
"Arabic script",
"مرحبا بالعالم",
- utf32_02,
+ utf32_03,
},
{
"Devanagari script",
"हैलो वर्ल्ड",
- utf32_03,
+ utf32_04,
},
{
"Emojis",
"\xF0\x9F\x98\x81 \xF0\x9F\x98\x82 \xF0\x9F\x98\x83 \xF0\x9F\x98\x84",
- utf32_04,
+ utf32_05,
},
};
- const unsigned int numberOfTests = 4u;
+ const unsigned int numberOfTests = 5u;
for( unsigned int index = 0u; index < numberOfTests; ++index )
{
// Tests the following functions with different scripts.
// Constructor, destructor and MultilanguageSupport::Get()
// void MultilanguageSupport::SetScripts( const Vector<Character>& text, const Vector<LineBreakInfo>& lineBreakInfo, Vector<ScriptRun>& scripts );
-// void MultilanguageSupport::ValidateFonts( const Vector<Character>& text, const Vector<ScriptRun>& scripts, Vector<FontRun>& fonts );
+// void MultilanguageSupport::ValidateFonts( const Vector<Character>& text,
+// const Vector<ScriptRun>& scripts,
+// const Vector<FontDescriptionRun>& fontDescriptions,
+// FontId defaultFontId,
+// Vector<FontRun>& fonts );
//////////////////////////////////////////////////////////
multilanguageSupport.SetScripts( utf32,
scripts );
+ // To be completed ...
+ Vector<FontDescriptionRun> fontDescriptions;
+ FontId defaultFontId = 0u;
Vector<FontRun> fonts;
+
// 3) Validate the fonts
multilanguageSupport.ValidateFonts( utf32,
scripts,
+ fontDescriptions,
+ defaultFontId,
fonts );
-
return true;
}
utc-Dali-ShadowView.cpp
utc-Dali-Slider.cpp
utc-Dali-TableView.cpp
+ utc-Dali-TextEditor.cpp
utc-Dali-TextField.cpp
utc-Dali-TextLabel.cpp
utc-Dali-TextSelectionPopup.cpp
dali-toolkit-test-utils/test-gl-sync-abstraction.cpp
dali-toolkit-test-utils/test-render-controller.cpp
dali-toolkit-test-utils/test-trace-call-stack.cpp
+ dali-toolkit-test-utils/test-native-image.cpp
)
PKG_CHECK_MODULES(${CAPI_LIB} REQUIRED
dali-core
- dali
+ dali-adaptor
dali-toolkit
)
void TestApplication::Initialize()
{
+ // We always need the first update!
+ mStatus.keepUpdating = Integration::KeepUpdating::STAGE_KEEP_RENDERING;
+
mCore = Dali::Integration::Core::New(
mRenderController,
mPlatformAbstraction,
void TestApplication::DoUpdate( unsigned int intervalMilliseconds )
{
+ if( GetUpdateStatus() == 0 &&
+ mRenderStatus.NeedsUpdate() == false &&
+ ! GetRenderController().WasCalled(TestRenderController::RequestUpdateFunc) )
+ {
+ fprintf(stderr, "WARNING - Update not required\n");
+ }
+
unsigned int nextVSyncTime = mLastVSyncTime + intervalMilliseconds;
float elapsedSeconds = intervalMilliseconds / 1e3f;
mCore->Update( elapsedSeconds, mLastVSyncTime, nextVSyncTime, mStatus );
+ GetRenderController().Initialize();
+
mLastVSyncTime = nextVSyncTime;
}
return mStatus.KeepUpdating();
}
+bool TestApplication::GetRenderNeedsUpdate()
+{
+ return mRenderStatus.NeedsUpdate();
+}
+bool TestApplication::GetRenderHasRendered()
+{
+ return mRenderStatus.HasRendered();
+}
+
bool TestApplication::RenderOnly( )
{
// Update Time values
bool UpdateOnly( unsigned int intervalMilliseconds = DEFAULT_RENDER_INTERVAL );
bool RenderOnly( );
void ResetContext();
+ bool GetRenderNeedsUpdate();
+ bool GetRenderHasRendered();
private:
void DoUpdate( unsigned int intervalMilliseconds );
mIsRenderbufferResult = 0;
mIsShaderResult = 0;
mIsTextureResult = 0;
- mVertexAttribArrayChanged = false;
-
+ mActiveTextureUnit = 0;
mCheckFramebufferStatusResult = 0;
mFramebufferStatus = 0;
mFramebufferColorAttached = 0;
mFramebufferDepthAttached = 0;
mFramebufferStencilAttached = 0;
-
mNumBinaryFormats = 0;
mBinaryFormats = 0;
mProgramBinaryLength = 0;
- mGetProgramBinaryCalled = false;
- mLastAutoTextureIdUsed = 0;
+ mVertexAttribArrayChanged = false;
+ mGetProgramBinaryCalled = false;
- mLastShaderIdUsed = 0;
- mLastProgramIdUsed = 0;
- mLastUniformIdUsed = 0;
mLastShaderCompiled = 0;
mLastClearBitMask = 0;
mClearCount = 0;
mLastBlendFuncDstRgb = 0;
mLastBlendFuncSrcAlpha = 0;
mLastBlendFuncDstAlpha = 0;
+ mLastAutoTextureIdUsed = 0;
+ mLastShaderIdUsed = 0;
+ mLastProgramIdUsed = 0;
+ mLastUniformIdUsed = 0;
mUniforms.clear();
mProgramUniforms1i.clear();
mProgramUniforms2f.clear();
mProgramUniforms3f.clear();
mProgramUniforms4f.clear();
+
+ for( unsigned int i=0; i<MAX_ATTRIBUTE_CACHE_SIZE; ++i )
+ {
+ mVertexAttribArrayState[i] = false;
+ }
}
void TestGlAbstraction::PreRender()
// EXTERNAL INCLUDES
#include <sstream>
#include <string>
+#include <cstring>
#include <map>
#include <cstdio>
#include <cstring> // for strcmp
inline void DeleteTextures(GLsizei n, const GLuint* textures)
{
std::stringstream out;
- out << n << ", " << textures << " = [" ;
+ out << n << ", " << textures << " = [";
for(GLsizei i=0; i<n; i++)
{
- out << textures[i] << ", " ;
+ out << textures[i] << ", ";
mDeletedTextureIds.push_back(textures[i]);
}
out << "]";
*/
TraceCallStack& TestGlSyncAbstraction::GetTrace() { return mTrace; }
+int TestGlSyncAbstraction::GetNumberOfSyncObjects()
+{
+ return mSyncObjects.size();
+}
+
} // Dali
*/
TraceCallStack& GetTrace();
+ /**
+ * Get the number of sync objects
+ *
+ * @return the number of sync objects
+ */
+ int GetNumberOfSyncObjects();
+
private:
typedef std::vector<TestSyncObject*> SyncContainer;
typedef SyncContainer::iterator SyncIter;
typedef std::map<int, TestCase> RunningTestCases;
-namespace
+const char* basename(const char* path)
{
-const char* RED_COLOR="\e[1;31m";
-const char* GREEN_COLOR="\e[1;32m";
-const char* ASCII_RESET="\e[0m";
-const char* ASCII_BOLD="\e[1m";
+ const char* ptr=path;
+ const char* slash=NULL;
+ for( ; *ptr != '\0' ; ++ptr )
+ {
+ if(*ptr == '/') slash=ptr;
+ }
+ if(slash != NULL) ++slash;
+ return slash;
}
-
int RunTestCase( struct ::testcase_s& testCase )
{
int result = EXIT_STATUS_TESTCASE_FAILED;
close(STDOUT_FILENO);
close(STDERR_FILENO);
}
- exit( RunTestCase( testCase ) );
+ else
+ {
+ printf("\n");
+ for(int i=0; i<80; ++i) printf("#");
+ printf("\nTC: %s\n", testCase.name);
+ fflush(stdout);
+ }
+
+ int status = RunTestCase( testCase );
+
+ if( ! suppressOutput )
+ {
+ fflush(stdout);
+ fflush(stderr);
+ fclose(stdout);
+ fclose(stderr);
+ }
+ exit( status );
}
else if(pid == -1)
{
else // Parent process
{
int status = 0;
- int childPid = waitpid(-1, &status, 0);
+ int childPid = waitpid(pid, &status, 0);
if( childPid == -1 )
{
perror("waitpid");
}
else if(WIFSIGNALED(status) )
{
+ int signal = WTERMSIG(status);
testResult = EXIT_STATUS_TESTCASE_ABORTED;
-
-#ifdef WCOREDUMP
- if(WCOREDUMP(status))
+ if( signal == SIGABRT )
+ {
+ printf("Test case %s failed: test case asserted\n", testCase.name );
+ }
+ else
{
- printf("Test case %s failed: due to a crash\n", testCase.name);
+ printf("Test case %s failed: exit with signal %s\n", testCase.name, strsignal(WTERMSIG(status)));
}
-#endif
- printf("Test case %s failed: exit with signal %s\n", testCase.name, strsignal(WTERMSIG(status)));
}
else if(WIFSTOPPED(status))
{
printf("Test case %s failed: stopped with signal %s\n", testCase.name, strsignal(WSTOPSIG(status)));
}
}
+ fflush(stdout);
+ fflush(stderr);
return testResult;
}
-void OutputStatistics( int numPasses, int numFailures )
+void OutputStatistics( const char* processName, int numPasses, int numFailures )
{
- const char* failureColor = GREEN_COLOR;
- if( numFailures > 0 )
+ FILE* fp=fopen("summary.xml", "a");
+ if( fp != NULL )
{
- failureColor = RED_COLOR;
+ fprintf( fp,
+ " <suite name=\"%s\">\n"
+ " <total_case>%d</total_case>\n"
+ " <pass_case>%d</pass_case>\n"
+ " <pass_rate>%5.2f</pass_rate>\n"
+ " <fail_case>%d</fail_case>\n"
+ " <fail_rate>%5.2f</fail_rate>\n"
+ " <block_case>0</block_case>\n"
+ " <block_rate>0.00</block_rate>\n"
+ " <na_case>0</na_case>\n"
+ " <na_rate>0.00</na_rate>\n"
+ " </suite>\n",
+ basename(processName),
+ numPasses+numFailures,
+ numPasses,
+ (float)numPasses/(numPasses+numFailures),
+ numFailures,
+ (float)numFailures/(numPasses+numFailures) );
+ fclose(fp);
}
- printf("\rNumber of test passes: %s%4d (%5.2f%%)%s\n", ASCII_BOLD, numPasses, 100.0f * (float)numPasses / (numPasses+numFailures), ASCII_RESET);
- printf("%sNumber of test failures:%s %s%4d%s\n", failureColor, ASCII_RESET, ASCII_BOLD, numFailures, ASCII_RESET);
-
}
-
-int RunAll(const char* processName, ::testcase tc_array[], bool reRunFailed)
+int RunAll( const char* processName, ::testcase tc_array[] )
{
int numFailures = 0;
int numPasses = 0;
// Run test cases in child process( to kill output/handle signals ), but run serially.
for( unsigned int i=0; tc_array[i].name; i++)
{
- int result = RunTestCaseInChildProcess( tc_array[i], true );
+ int result = RunTestCaseInChildProcess( tc_array[i], false );
if( result == 0 )
{
numPasses++;
}
}
- OutputStatistics(numPasses, numFailures);
+ OutputStatistics( processName, numPasses, numFailures);
return numFailures;
}
-
-
// Constantly runs up to MAX_NUM_CHILDREN processes
int RunAllInParallel( const char* processName, ::testcase tc_array[], bool reRunFailed)
{
}
}
- OutputStatistics( numPasses, numFailures );
+ OutputStatistics( processName, numPasses, numFailures );
if( reRunFailed )
{
* Run all test cases in serial
* @param[in] processName The name of this process
* @param[in] tc_array The array of auto-generated testkit-lite test cases
- * @param[in] reRunFailed True if failed test cases should be re-run
* @return 0 on success
*/
-int RunAll(const char* processName, testcase tc_array[], bool reRunFailed);
+int RunAll( const char* processName, testcase tc_array[] );
/**
* Find the named test case in the given array, and run it
TestNativeImage::TestNativeImage(int width, int height)
: mWidth(width), mHeight(height), mExtensionCreateCalls(0), mExtensionDestroyCalls(0), mTargetTextureCalls(0)
{
+ mExtension = new TestNativeImageExtension();
}
TestNativeImage::~TestNativeImage()
// INTERNAL INCLUDES
#include <dali/public-api/images/native-image-interface.h>
+#include <dali/devel-api/images/native-image-interface-extension.h>
namespace Dali
{
class TestNativeImage;
typedef IntrusivePtr<TestNativeImage> TestNativeImagePointer;
+class DALI_IMPORT_API TestNativeImageExtension: public Dali::NativeImageInterface::Extension
+{
+public:
+ inline const char* GetCustomFragmentPreFix(){return "#extension GL_OES_EGL_image_external:require\n";}
+ inline const char* GetCustomSamplerTypename(){return "samplerExternalOES";}
+
+};
+
class DALI_IMPORT_API TestNativeImage : public Dali::NativeImageInterface
{
public:
inline virtual unsigned int GetWidth() const {return mWidth;};
inline virtual unsigned int GetHeight() const {return mHeight;};
inline virtual bool RequiresBlending() const {return true;};
+ inline virtual Dali::NativeImageInterface::Extension* GetExtension() {return mExtension;}
private:
TestNativeImage(int width, int height);
int mExtensionCreateCalls;
int mExtensionDestroyCalls;
int mTargetTextureCalls;
+ TestNativeImageExtension* mExtension;
};
} // Dali
return numCalls;
}
-
/**
* Search for a method in the stack with the given parameter list
* @param[in] method The name of the method
*/
bool TraceCallStack::FindMethodAndParams(std::string method, std::string params) const
{
- bool found = false;
+ return FindIndexFromMethodAndParams( method, params ) > -1;
+}
+
+/**
+ * Search for a method in the stack with the given parameter list
+ * @param[in] method The name of the method
+ * @param[in] params A comma separated list of parameter values
+ * @return index in the stack where the method was found or -1 otherwise
+ */
+int TraceCallStack::FindIndexFromMethodAndParams(std::string method, std::string params) const
+{
+ int index = -1;
for( size_t i=0; i < mCallStack.size(); i++ )
{
if( 0 == mCallStack[i][0].compare(method) && 0 == mCallStack[i][1].compare(params) )
{
- found = true;
+ index = i;
break;
}
}
- return found;
+ return index;
}
/**
bool FindMethodAndParams(std::string method, std::string params) const;
/**
+ * Search for a method in the stack with the given parameter list
+ * @param[in] method The name of the method
+ * @param[in] params A comma separated list of parameter values
+ * @return index in the stack where the method was found or -1 otherwise
+ */
+ int FindIndexFromMethodAndParams(std::string method, std::string params) const;
+
+ /**
* Test if the given method and parameters are at a given index in the stack
* @param[in] index Index in the call stack
* @param[in] method Name of method to test
// INTERNAL INCLUDES
#include <dali-test-suite-utils.h>
+#include <dali/devel-api/text-abstraction/font-client.h>
#include "toolkit-orientation.h"
: TestApplication( false, surfaceWidth, surfaceHeight, horizontalDpi, verticalDpi )
{
Initialize();
+
+ // set the DPI value for font rendering
+ Dali::TextAbstraction::FontClient fontClient = Dali::TextAbstraction::FontClient::Get();
+ if( fontClient )
+ {
+ fontClient.SetDpi( mDpi.x, mDpi.y );
+ }
}
~ToolkitTestApplication()
{
int result = TestHarness::EXIT_STATUS_BAD_ARGUMENT;
- const char* optString = "r";
- bool optRerunFailed(false);
+ const char* optString = "rs";
+ bool optRerunFailed(true);
+ bool optRunSerially(false);
int nextOpt = 0;
do
case 'r':
optRerunFailed = true;
break;
+ case 's':
+ optRunSerially = true;
+ break;
case '?':
TestHarness::Usage(argv[0]);
exit(TestHarness::EXIT_STATUS_BAD_ARGUMENT);
if( optind == argc ) // no testcase name in argument list
{
- result = TestHarness::RunAllInParallel(argv[0], tc_array, optRerunFailed);
+ if( optRunSerially )
+ {
+ result = TestHarness::RunAll( argv[0], tc_array );
+ }
+ else
+ {
+ result = TestHarness::RunAllInParallel( argv[0], tc_array, optRerunFailed );
+ }
}
else
{
END_TEST;
}
-int UtcDaliBubbleEmitterSetBlendMode(void)
-{
- ToolkitTestApplication application;
- tet_infoline( " UtcDaliBubbleEmitterSetBlendMode " );
-
- Image shapeImage = CreateSolidColorImage( application, Color::GREEN, 5, 5 );
- BubbleEmitter emitter = BubbleEmitter::New( Vector2(50.f,50.f),shapeImage, 150, Vector2( 5.f, 10.f ));
- DALI_TEST_CHECK(emitter);
- Actor root = emitter.GetRootActor();
- Stage::GetCurrent().Add( root );
- root.SetPosition( Vector3::ZERO );
- root.SetParentOrigin( ParentOrigin::CENTER );
- root.SetAnchorPoint( AnchorPoint::CENTER );
-
- TestGlAbstraction& glAbstraction = application.GetGlAbstraction();
- Wait(application);
- DALI_TEST_EQUALS( (GLenum)GL_SRC_ALPHA, glAbstraction.GetLastBlendFuncSrcRgb(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE_MINUS_SRC_ALPHA, glAbstraction.GetLastBlendFuncDstRgb(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE, glAbstraction.GetLastBlendFuncSrcAlpha(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE_MINUS_SRC_ALPHA, glAbstraction.GetLastBlendFuncDstAlpha(), TEST_LOCATION );
-
- emitter.SetBlendMode( true );
- Wait(application);
- DALI_TEST_EQUALS( (GLenum)GL_SRC_ALPHA, glAbstraction.GetLastBlendFuncSrcRgb(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE, glAbstraction.GetLastBlendFuncDstRgb(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ZERO, glAbstraction.GetLastBlendFuncSrcAlpha(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE, glAbstraction.GetLastBlendFuncDstAlpha(), TEST_LOCATION );
-
- emitter.SetBlendMode( false );
- Wait(application);
- DALI_TEST_EQUALS( (GLenum)GL_SRC_ALPHA, glAbstraction.GetLastBlendFuncSrcRgb(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE_MINUS_SRC_ALPHA, glAbstraction.GetLastBlendFuncDstRgb(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE, glAbstraction.GetLastBlendFuncSrcAlpha(), TEST_LOCATION );
- DALI_TEST_EQUALS( (GLenum)GL_ONE_MINUS_SRC_ALPHA, glAbstraction.GetLastBlendFuncDstAlpha(), TEST_LOCATION );
-
- END_TEST;
-}
-
int UtcDaliBubbleEmitterEmitBubble(void)
{
ToolkitTestApplication application;
" \"vertexPrefix\": \"\",\n"
" \"vertex\": \"void main(void)\\n{\\n gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);\\n vTexCoord = aTexCoord;\\n}\\n\\n\",\n"
" \"fragmentPrefix\": \"\",\n"
- " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = uTextureRect.zw - uTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
+ " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = sTextureRect.zw - sTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
" \"geometryType\": \"GEOMETRY_TYPE_IMAGE\"\n"
" },\n"
" \"geometryHints\": \"HINT_NONE\",\n"
" \"vertexPrefix\": \"\",\n"
" \"vertex\": \"void main(void)\\n{\\n gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);\\n vTexCoord = aTexCoord;\\n}\\n\\n\",\n"
" \"fragmentPrefix\": \"\",\n"
- " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = uTextureRect.zw - uTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
+ " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = sTextureRect.zw - sTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
" \"geometryType\": \"GEOMETRY_TYPE_IMAGE\"\n"
" },\n"
" \"geometryHints\": \"HINT_NONE\",\n"
" \"vertexPrefix\": \"\",\n"
" \"vertex\": \"void main(void)\\n{\\n gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);\\n vTexCoord = aTexCoord;\\n}\\n\\n\",\n"
" \"fragmentPrefix\": \"\",\n"
- " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = uTextureRect.zw - uTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
+ " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = sTextureRect.zw - sTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
" \"geometryType\": \"GEOMETRY_TYPE_IMAGE\"\n"
" },\n"
" \"geometryHints\": \"HINT_NONE\",\n"
" \"vertexPrefix\": \"\",\n"
" \"vertex\": \"void main(void)\\n{\\n gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);\\n vTexCoord = aTexCoord;\\n}\\n\\n\",\n"
" \"fragmentPrefix\": \"\",\n"
- " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = uTextureRect.zw - uTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
+ " \"fragment\": \"precision mediump float;\\nuniform float uAmplitude; // 0.02; (< 1)\\nuniform float uTime;\\nvoid main()\\n{\\n highp vec2 textureSize = sTextureRect.zw - sTextureRect.xy;\\n highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\\n highp float len = length(pos);\\n highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude; \\n gl_FragColor = texture2D(sTexture, texCoord) * uColor;\\n}\\n\\n\\n\",\n"
" \"geometryType\": \"GEOMETRY_TYPE_IMAGE\"\n"
" },\n"
" \"geometryHints\": \"HINT_NONE\",\n"
Stage::GetCurrent().Add( actor );
controlRenderer.SetOnStage( actor );
- DALI_TEST_EQUALS( actor.GetRendererAt(0u).GetDepthIndex(), 1, TEST_LOCATION );
+ int depthIndex = actor.GetRendererAt(0u).GetProperty<int>( Renderer::Property::DEPTH_INDEX );
+ DALI_TEST_EQUALS( depthIndex, 1, TEST_LOCATION );
DALI_TEST_EQUALS( controlRenderer.GetDepthIndex(), 1.f, TEST_LOCATION );
controlRenderer.SetDepthIndex( -1.f );
- DALI_TEST_EQUALS( actor.GetRendererAt(0u).GetDepthIndex(), -1, TEST_LOCATION );
+ depthIndex = actor.GetRendererAt(0u).GetProperty<int>( Renderer::Property::DEPTH_INDEX );
+ DALI_TEST_EQUALS( depthIndex, -1, TEST_LOCATION );
DALI_TEST_EQUALS( controlRenderer.GetDepthIndex(), -1.f, TEST_LOCATION );
END_TEST;
#include <dali-toolkit/dali-toolkit.h>
#include <dali/devel-api/scripting/scripting.h>
+#include <dali/devel-api/rendering/renderer.h>
+
+#include <test-native-image.h>
+#include <sstream>
using namespace Dali;
using namespace Toolkit;
namespace
{
+
+const char* VERTEX_SHADER = DALI_COMPOSE_SHADER(
+ attribute mediump vec2 aPosition;\n
+ varying mediump vec2 vTexCoord;\n
+ uniform mediump mat4 uMvpMatrix;\n
+ uniform mediump vec3 uSize;\n
+ \n
+ void main()\n
+ {\n
+ mediump vec4 vertexPosition = vec4(aPosition, 0.0, 1.0);\n
+ vertexPosition.xyz *= uSize;\n
+ vertexPosition = uMvpMatrix * vertexPosition;\n
+ \n
+ vTexCoord = aPosition + vec2(0.5);\n
+ gl_Position = vertexPosition;\n
+ }\n
+);
+
+const char* FRAGMENT_SHADER = DALI_COMPOSE_SHADER(
+ varying mediump vec2 vTexCoord;\n
+ uniform sampler2D sTexture;\n
+ uniform lowp vec4 uColor;\n
+ \n
+ void main()\n
+ {\n
+ gl_FragColor = texture2D( sTexture, vTexCoord ) * uColor;\n
+ }\n
+);
+
const char* TEST_IMAGE_FILE_NAME = "gallery_image_01.jpg";
const char* TEST_IMAGE_FILE_NAME2 = "gallery_image_02.jpg";
END_TEST;
}
+int UtcDaliImageViewSetGetProperty02(void)
+{
+ ToolkitTestApplication application;
+
+ Image image = CreateBufferImage( 10, 10, Color::WHITE );
+ ImageView imageView = ImageView::New(image);
+ Vector4 fullImageRect( 0.f, 0.f, 1.f, 1.f );
+
+ Stage::GetCurrent().Add( imageView );
+
+ application.SendNotification();
+ application.Render();
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+
+ Vector4 pixelAreaUniform;
+ DALI_TEST_CHECK( gl.GetUniformValue<Vector4>( "pixelArea", pixelAreaUniform ) );
+ DALI_TEST_EQUALS( pixelAreaUniform, fullImageRect, TEST_LOCATION );
+
+ Property::Value value = imageView.GetProperty( ImageView::Property::PIXEL_AREA );
+ Vector4 pixelAreaValue;
+ DALI_TEST_CHECK( value.Get(pixelAreaValue) );
+ DALI_TEST_EQUALS( pixelAreaValue, fullImageRect, TEST_LOCATION );
+
+ Vector4 pixelAreaSet( 0.2f, 0.2f, 0.3f, 0.3f );
+ imageView.SetProperty( ImageView::Property::PIXEL_AREA, pixelAreaSet);
+
+ application.SendNotification();
+ application.Render();
+
+ value = imageView.GetProperty( ImageView::Property::PIXEL_AREA );
+ value.Get(pixelAreaValue);
+ DALI_TEST_EQUALS( pixelAreaValue, pixelAreaSet, TEST_LOCATION );
+
+ DALI_TEST_CHECK( gl.GetUniformValue<Vector4>( "pixelArea", pixelAreaUniform ) );
+ DALI_TEST_EQUALS( pixelAreaUniform, pixelAreaSet, TEST_LOCATION );
+
+ END_TEST;
+}
+
+int UtcDaliImageViewSetGetProperty03(void)
+{
+ ToolkitTestApplication application;
+
+ Image image = CreateBufferImage( 10, 10, Color::WHITE );
+ ImageView imageView = ImageView::New(image);
+ Stage::GetCurrent().Add( imageView );
+ application.SendNotification();
+ application.Render();
+
+ // conventional alpha blending
+ Renderer renderer = imageView.GetRendererAt( 0 );
+ BlendingFactor::Type srcFactorRgb;
+ BlendingFactor::Type destFactorRgb;
+ BlendingFactor::Type srcFactorAlpha;
+ BlendingFactor::Type destFactorAlpha;
+ renderer.GetBlendFunc(srcFactorRgb, destFactorRgb, srcFactorAlpha, destFactorAlpha);
+ DALI_TEST_CHECK( srcFactorRgb == BlendingFactor::SRC_ALPHA );
+ DALI_TEST_CHECK( destFactorRgb == BlendingFactor::ONE_MINUS_SRC_ALPHA );
+ DALI_TEST_CHECK( srcFactorAlpha == BlendingFactor::ONE );
+ DALI_TEST_CHECK( destFactorAlpha == BlendingFactor::ONE_MINUS_SRC_ALPHA );
+
+ Property::Value value = renderer.GetProperty( Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA );
+ bool enable;
+ DALI_TEST_CHECK( value.Get( enable ) );
+ DALI_TEST_CHECK( !enable );
+
+ // pre-multiplied alpha blending
+ imageView.SetProperty( Toolkit::ImageView::Property::PRE_MULTIPLIED_ALPHA, true );
+ application.SendNotification();
+ application.Render();
+
+ renderer.GetBlendFunc(srcFactorRgb, destFactorRgb, srcFactorAlpha, destFactorAlpha);
+ DALI_TEST_CHECK( srcFactorRgb == BlendingFactor::ONE );
+ DALI_TEST_CHECK( destFactorRgb == BlendingFactor::ONE_MINUS_SRC_ALPHA );
+ DALI_TEST_CHECK( srcFactorAlpha == BlendingFactor::ONE );
+ DALI_TEST_CHECK( destFactorAlpha == BlendingFactor::ONE );
+
+ value = renderer.GetProperty( Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA );
+ DALI_TEST_CHECK( value.Get( enable ) );
+ DALI_TEST_CHECK( enable );
+
+ END_TEST;
+}
+
int UtcDaliImageViewSizeWithBackground(void)
{
ToolkitTestApplication application;
END_TEST;
}
+
+// Scenarios 1: ImageView from regular image
+int UtcDaliImageViewSetImageBufferImage(void)
+{
+ ToolkitTestApplication application;
+
+ ImageView imageView = ImageView::New();
+ Stage::GetCurrent().Add( imageView );
+
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+ gl.EnableTextureCallTrace( true );
+
+ std::vector< GLuint > ids;
+ ids.push_back( 23 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ int width = 300;
+ int height = 400;
+ BufferImage image = CreateBufferImage( width, height, Color::WHITE );
+
+ imageView.SetImage( image );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream params;
+ params << GL_TEXTURE_2D << ", " << 23;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", params.str()) );
+
+ END_TEST;
+}
+
+// Scenarios 2: ImageView from Native image
+int UtcDaliImageViewSetImageNativeImage(void)
+{
+ ToolkitTestApplication application;
+
+ ImageView imageView = ImageView::New();
+ Stage::GetCurrent().Add( imageView );
+
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+ gl.EnableTextureCallTrace( true );
+
+ std::vector< GLuint > ids;
+ ids.push_back( 23 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ int width = 200;
+ int height = 500;
+ TestNativeImagePointer nativeImageInterface = TestNativeImage::New( width, height );
+ NativeImage nativeImage = NativeImage::New( *(nativeImageInterface.Get()) );
+
+ imageView.SetImage( nativeImage );
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream params;
+ params << GL_TEXTURE_2D << ", " << 23;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", params.str()) );
+
+ END_TEST;
+}
+
+// Scenarios 3: ImageView initially from regular image but then SetImage called with Native image
+int UtcDaliImageViewSetImageBufferImageToNativeImage(void)
+{
+ ToolkitTestApplication application;
+
+ int width = 300;
+ int height = 400;
+ BufferImage image = CreateBufferImage( width, height, Color::WHITE );
+
+ ImageView imageView = ImageView::New( image );
+ Stage::GetCurrent().Add( imageView );
+
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+ gl.EnableTextureCallTrace( true );
+
+ std::vector< GLuint > ids;
+ ids.push_back( 23 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream params;
+ params << GL_TEXTURE_2D << ", " << 23;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", params.str()) );
+
+ width = 200;
+ height = 500;
+ TestNativeImagePointer nativeImageInterface = TestNativeImage::New( width, height );
+ NativeImage nativeImage = NativeImage::New( *(nativeImageInterface.Get()) );
+ imageView.SetImage( nativeImage );
+
+ ids.clear();
+ ids.push_back( 24 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream nextTextureParams;
+ nextTextureParams << GL_TEXTURE_2D << ", " << 24;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", nextTextureParams.str()) );
+
+ END_TEST;
+}
+
+// Scenarios 4: ImageView initially from Native image but then SetImage called with regular image
+int UtcDaliImageViewSetImageNativeImageToBufferImage(void)
+{
+ ToolkitTestApplication application;
+
+ int width = 300;
+ int height = 400;
+ TestNativeImagePointer nativeImageInterface = TestNativeImage::New( width, height );
+ NativeImage nativeImage = NativeImage::New( *(nativeImageInterface.Get()) );
+
+ ImageView imageView = ImageView::New( nativeImage );
+ Stage::GetCurrent().Add( imageView );
+
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+ gl.EnableTextureCallTrace( true );
+
+ std::vector< GLuint > ids;
+ ids.push_back( 23 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream params;
+ params << GL_TEXTURE_2D << ", " << 23;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", params.str()) );
+
+ width = 200;
+ height = 500;
+ BufferImage image = CreateBufferImage( width, height, Color::WHITE );
+ imageView.SetImage( image );
+
+ ids.clear();
+ ids.push_back( 24 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream nextTextureParams;
+ nextTextureParams << GL_TEXTURE_2D << ", " << 24;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", nextTextureParams.str()) );
+
+ END_TEST;
+}
+
+// Scenarios 5: ImageView from Native image with custom shader
+int UtcDaliImageViewSetImageNativeImageWithCustomShader(void)
+{
+ ToolkitTestApplication application;
+
+ int width = 300;
+ int height = 400;
+
+ Property::Map customShader;
+ customShader.Insert( "vertexShader", VERTEX_SHADER );
+ customShader.Insert( "fragmentShader", FRAGMENT_SHADER );
+
+ Property::Array shaderHints;
+ shaderHints.PushBack( "requiresSelfDepthTest" );
+ shaderHints.PushBack( "outputIsTransparent" );
+ shaderHints.PushBack( "outputIsOpaque" );
+ shaderHints.PushBack( "modifiesGeometry" );
+
+ customShader.Insert( "hints", shaderHints );
+
+ Property::Map map;
+ map.Insert( "rendererType", "imageRenderer" );
+ map.Insert( "shader", customShader );
+
+ TestNativeImagePointer nativeImageInterface = TestNativeImage::New( width, height );
+ NativeImage nativeImage = NativeImage::New( *(nativeImageInterface.Get()) );
+
+ ImageView imageView = ImageView::New( nativeImage );
+ imageView.SetProperty( ImageView::Property::IMAGE, map );
+ Stage::GetCurrent().Add( imageView );
+
+ imageView.SetProperty( ImageView::Property::IMAGE, map );
+
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+ gl.EnableTextureCallTrace( true );
+
+ std::vector< GLuint > ids;
+ ids.push_back( 23 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream params;
+ params << GL_TEXTURE_2D << ", " << 23;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", params.str()) );
+
+ END_TEST;
+}
+
+// Scenarios 6: ImageView initially from regular image with custom shader but then SetImage called with Native
+int UtcDaliImageViewSetImageBufferImageWithCustomShaderToNativeImage(void)
+{
+ ToolkitTestApplication application;
+
+ int width = 300;
+ int height = 400;
+
+ Property::Map customShader;
+ customShader.Insert( "vertexShader", VERTEX_SHADER );
+ customShader.Insert( "fragmentShader", FRAGMENT_SHADER );
+
+ Property::Array shaderHints;
+ shaderHints.PushBack( "requiresSelfDepthTest" );
+ shaderHints.PushBack( "outputIsTransparent" );
+ shaderHints.PushBack( "outputIsOpaque" );
+ shaderHints.PushBack( "modifiesGeometry" );
+
+ customShader.Insert( "hints", shaderHints );
+
+ Property::Map map;
+ map.Insert( "rendererType", "imageRenderer" );
+ map.Insert( "shader", customShader );
+
+ BufferImage image = CreateBufferImage( width, height, Color::WHITE );
+
+ ImageView imageView = ImageView::New( image );
+ imageView.SetProperty( ImageView::Property::IMAGE, map );
+ Stage::GetCurrent().Add( imageView );
+
+ imageView.SetProperty( ImageView::Property::IMAGE, map );
+
+ TestGlAbstraction& gl = application.GetGlAbstraction();
+ gl.EnableTextureCallTrace( true );
+
+ std::vector< GLuint > ids;
+ ids.push_back( 23 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream params;
+ params << GL_TEXTURE_2D << ", " << 23;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", params.str()) );
+
+ TestNativeImagePointer nativeImageInterface = TestNativeImage::New( width, height );
+ NativeImage nativeImage = NativeImage::New( *(nativeImageInterface.Get()) );
+ imageView.SetImage( nativeImage );
+
+ ids.clear();
+ ids.push_back( 24 );
+ application.GetGlAbstraction().SetNextTextureIds( ids );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethod("BindTexture") );
+
+ std::stringstream nativeImageParams;
+ nativeImageParams << GL_TEXTURE_2D << ", " << 24;
+ DALI_TEST_CHECK( gl.GetTextureTrace().FindMethodAndParams("BindTexture", nativeImageParams.str()) );
+
+
+ END_TEST;
+}
END_TEST;
}
+
+int UtcDaliItemViewSetGetProperty(void)
+{
+ ToolkitTestApplication application;
+
+ // Create the ItemView actor
+ TestItemFactory factory;
+ ItemView view = ItemView::New(factory);
+ DALI_TEST_CHECK(view);
+
+ // Event side properties
+
+ // Test "minimumSwipeSpeed" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("minimumSwipeSpeed") == ItemView::Property::MINIMUM_SWIPE_SPEED );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::MINIMUM_SWIPE_SPEED).Get<float>(), view.GetMinimumSwipeSpeed(), TEST_LOCATION );
+ view.SetProperty( ItemView::Property::MINIMUM_SWIPE_SPEED, 2.5f );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::MINIMUM_SWIPE_SPEED).Get<float>(), 2.5f, TEST_LOCATION );
+
+ // Test "minimumSwipeDistance" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("minimumSwipeDistance") == ItemView::Property::MINIMUM_SWIPE_DISTANCE );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::MINIMUM_SWIPE_DISTANCE).Get<float>(), view.GetMinimumSwipeDistance(), TEST_LOCATION );
+ view.SetProperty( ItemView::Property::MINIMUM_SWIPE_DISTANCE, 8.725f );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::MINIMUM_SWIPE_DISTANCE).Get<float>(), 8.725f, TEST_LOCATION );
+
+ // Test "wheelScrollDistanceStep" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("wheelScrollDistanceStep") == ItemView::Property::WHEEL_SCROLL_DISTANCE_STEP );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::WHEEL_SCROLL_DISTANCE_STEP).Get<float>(), view.GetWheelScrollDistanceStep(), TEST_LOCATION );
+ view.SetProperty( ItemView::Property::WHEEL_SCROLL_DISTANCE_STEP, 5.0f );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::WHEEL_SCROLL_DISTANCE_STEP).Get<float>(), 5.0f, TEST_LOCATION );
+
+ // Test "snapToItemEnabled" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("snapToItemEnabled") == ItemView::Property::SNAP_TO_ITEM_ENABLED );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::SNAP_TO_ITEM_ENABLED).Get<bool>(), view.GetAnchoring(), TEST_LOCATION );
+ view.SetProperty( ItemView::Property::SNAP_TO_ITEM_ENABLED, true );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::SNAP_TO_ITEM_ENABLED).Get<bool>(), true, TEST_LOCATION );
+
+ // Test "refreshInterval" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("refreshInterval") == ItemView::Property::REFRESH_INTERVAL );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::REFRESH_INTERVAL).Get<float>(), view.GetRefreshInterval(), TEST_LOCATION );
+ view.SetProperty( ItemView::Property::REFRESH_INTERVAL, 11.0f );
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::REFRESH_INTERVAL).Get<float>(), 11.0f, TEST_LOCATION );
+
+ // Test "overshootEnabled" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("overshootEnabled") == Scrollable::Property::OVERSHOOT_ENABLED );
+ DALI_TEST_EQUALS( view.GetProperty(Scrollable::Property::OVERSHOOT_ENABLED).Get<bool>(), view.IsOvershootEnabled(), TEST_LOCATION );
+ view.SetProperty( Scrollable::Property::OVERSHOOT_ENABLED, false );
+ DALI_TEST_EQUALS( view.GetProperty(Scrollable::Property::OVERSHOOT_ENABLED).Get<bool>(), false, TEST_LOCATION );
+
+ // Animatable properties
+
+ // Test "layoutPosition" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("layoutPosition") == ItemView::Property::LAYOUT_POSITION );
+ view.SetProperty( ItemView::Property::LAYOUT_POSITION, 20.5f );
+ Wait(application);
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::LAYOUT_POSITION).Get<float>(), 20.5f, TEST_LOCATION );
+
+ // Test "scrollSpeed" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("scrollSpeed") == ItemView::Property::SCROLL_SPEED );
+ view.SetProperty( ItemView::Property::SCROLL_SPEED, 3.35f );
+ Wait(application);
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::SCROLL_SPEED).Get<float>(), 3.35f, TEST_LOCATION );
+
+ // Test "overshoot" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("overshoot") == ItemView::Property::OVERSHOOT );
+ view.SetProperty( ItemView::Property::OVERSHOOT, 0.15f );
+ Wait(application);
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::OVERSHOOT).Get<float>(), 0.15f, TEST_LOCATION );
+
+ // Test "scrollDirection" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("scrollDirection") == ItemView::Property::SCROLL_DIRECTION );
+ view.SetProperty( ItemView::Property::SCROLL_DIRECTION, Vector2(0.85f, 0.5f) );
+ Wait(application);
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::SCROLL_DIRECTION).Get<Vector2>(), Vector2(0.85f, 0.5f), TEST_LOCATION );
+
+ // Test "layoutOrientation" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("layoutOrientation") == ItemView::Property::LAYOUT_ORIENTATION );
+ view.SetProperty( ItemView::Property::LAYOUT_ORIENTATION, 2 );
+ Wait(application);
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::LAYOUT_ORIENTATION).Get<int>(), 2, TEST_LOCATION );
+
+ // Test "scrollContentSize" property
+ DALI_TEST_CHECK( view.GetPropertyIndex("scrollContentSize") == ItemView::Property::SCROLL_CONTENT_SIZE );
+ view.SetProperty( ItemView::Property::SCROLL_CONTENT_SIZE, 250.0f );
+ Wait(application);
+ DALI_TEST_EQUALS( view.GetProperty(ItemView::Property::SCROLL_CONTENT_SIZE).Get<float>(), 250.0f, TEST_LOCATION );
+
+ END_TEST;
+}
+
tet_result(TET_PASS);
END_TEST;
}
+
+
+int UtcDaliJsonParserMerge1(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline("JSON tree merge");
+
+ std::string s1( ReplaceQuotes(" \
+{ \
+ 'styles': \
+ { \
+ 'button': \
+ { \
+ 'backgroundColor':[0.8, 0.0, 1.0, 1.0], \
+ 'foregroundColor':[1, 1, 1, 1] \
+ } \
+ } \
+} \
+"));
+
+ JsonParser parser = JsonParser::New();
+ JsonParser testParser = JsonParser::New();
+
+ testParser.Parse( s1 );
+
+ parser.Parse( s1 );
+ parser.Parse( s1 ); // Merge the tree into itself. The value array should not grow.
+
+ DALI_TEST_CHECK(parser.GetRoot());
+
+ CompareTrees( *parser.GetRoot(), *testParser.GetRoot() );
+
+ END_TEST;
+}
ToolkitTestApplication application;
tet_infoline(" UtcDaliPushButtonAlignmentLayout");
- // This test checks different alignments for the icon against the label.
- // The icon is then moved around the label in each of it's alignments.
- // The final relayed out size is checked to confirm the layout has been done correctly.
+ /*
+ * This test checks different alignments for the icon against the label.
+ * The icon is then moved around the label in each of it's alignments.
+ * The final relayed out size is checked to confirm the layout has been done correctly.
+ *
+ * There is an Icon which has 0 width and height, but with 75 padding on all sides.
+ * - Therefore total width and height are both 150.
+ *
+ * There is a Label which has "an unknown" width and height, but with 30 padding on all sides.
+ * - Therefore total width and height are 60+x and 60+y respectively.
+ * Where x & y are the width and height of the text.
+ *
+ * The width of the button will always expand to the largest of the icon and label sizes (plus padding).
+ * So We use the padding to help us determine the orientation is correct for each alignment.
+ *
+ * |<- 150 ->| |<-- 60+x -->|
+ *
+ * +---------+ -
+ * | | ^ +------------+ -
+ * | | | | | ^
+ * | Icon | 150 | Label | 60+y
+ * | | | | | v
+ * | | v +------------+ -
+ * +---------+ -
+ */
PushButton pushButton = PushButton::New();
pushButton.SetProperty( Toolkit::PushButton::Property::LABEL_PADDING, Vector4( 30.0f, 30.0f, 30.0f, 30.0f ) );
size.width = pushButton.GetRelayoutSize( Dimension::WIDTH );
size.height = pushButton.GetRelayoutSize( Dimension::HEIGHT );
+
+ /*
+ * Test Icon right alignment.
+ * Height grows to largest of Icon or Label (+ padding).
+ * Normally this will be Icons height, except with very large font sizes.
+ *
+ * +------------+---------+
+ * |............+ |
+ * | | |
+ * | Label | Icon |
+ * | | |
+ * |............+ |
+ * +------------+---------+
+ */
DALI_TEST_GREATER( size.width, 150.0f + 60.0f, TEST_LOCATION );
DALI_TEST_EQUALS( size.height, 150.0f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
compareSize.width = pushButton.GetRelayoutSize( Dimension::WIDTH );
compareSize.height = pushButton.GetRelayoutSize( Dimension::HEIGHT );
+ /*
+ * Test Icon left alignment.
+ * Height grows to largest of Icon or Label (+ padding).
+ * Normally this will be Icons height, except with very large font sizes.
+ *
+ * +---------+------------+
+ * | +............|
+ * | | |
+ * | Icon | Label |
+ * | | |
+ * | +............|
+ * +---------+------------+
+ */
DALI_TEST_EQUALS( size, compareSize, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
// Test top alignment.
compareSize.width = pushButton.GetRelayoutSize( Dimension::WIDTH );
compareSize.height = pushButton.GetRelayoutSize( Dimension::HEIGHT );
- DALI_TEST_EQUALS( compareSize.width, 150.0f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+ /*
+ * Test Icon top alignment.
+ * Width grows to largest of Icon or Label (+ padding).
+ *
+ * +---------+
+ * | |
+ * | |
+ * | Icon |
+ * | |
+ * | |
+ * +---------+
+ * | |
+ * | Label |
+ * | |
+ * +---------+
+ *
+ * Note: We subtract a small number as we want to do a >= test.
+ */
+ DALI_TEST_GREATER( size.width, 150.0f - Math::MACHINE_EPSILON_1000, TEST_LOCATION );
DALI_TEST_GREATER( compareSize.height, 150.0f + 60.0f, TEST_LOCATION );
// Test bottom alignment.
size.width = pushButton.GetRelayoutSize( Dimension::WIDTH );
size.height = pushButton.GetRelayoutSize( Dimension::HEIGHT );
+ /*
+ * Test Icon bottom alignment.
+ * Width grows to largest of Icon or Label (+ padding).
+ *
+ * +---------+
+ * | |
+ * | Label |
+ * | |
+ * +---------+
+ * | |
+ * | |
+ * | Icon |
+ * | |
+ * | |
+ * +---------+
+ */
DALI_TEST_EQUALS( size, compareSize, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
END_TEST;
controlRenderer.SetOnStage( actor );
DALI_TEST_CHECK( actor.GetRendererCount() == 1u );
+ int blendMode = actor.GetRendererAt(0u).GetProperty<int>( Renderer::Property::BLENDING_MODE );
+ DALI_TEST_EQUALS( static_cast<BlendingMode::Type>(blendMode), BlendingMode::ON, TEST_LOCATION );
TestGlAbstraction& gl = application.GetGlAbstraction();
RendererFactory factory = RendererFactory::Get();
DALI_TEST_CHECK( factory );
- Vector4 testColor( 1.f, 0.5f, 0.3f, 0.2f );
+ Vector4 testColor( 1.f, 0.5f, 0.3f, 1.f );
float testSize = 5.f;
- ControlRenderer controlRenderer = factory.GetControlRenderer(testSize, testColor);
+ ControlRenderer controlRenderer = factory.GetControlRenderer(testSize, testColor );
DALI_TEST_CHECK( controlRenderer );
Actor actor = Actor::New();
application.SendNotification();
application.Render(0);
+ int blendMode = actor.GetRendererAt(0u).GetProperty<int>( Renderer::Property::BLENDING_MODE );
+ DALI_TEST_EQUALS( static_cast<BlendingMode::Type>(blendMode), BlendingMode::AUTO, TEST_LOCATION );
+
Vector4 actualColor(Vector4::ZERO);
DALI_TEST_CHECK( gl.GetUniformValue<Vector4>( "borderColor", actualColor ) );
DALI_TEST_EQUALS( actualColor, testColor, TEST_LOCATION );
DALI_TEST_CHECK( gl.GetUniformValue<float>( "borderSize", actualSize ) );
DALI_TEST_EQUALS( actualSize, testSize, TEST_LOCATION );
+ controlRenderer.SetOffStage( actor );
+
+ // enable the anti-aliasing
+ controlRenderer = factory.GetControlRenderer(testSize, testColor, true );
+ controlRenderer.SetOnStage( actor );
+
+ application.SendNotification();
+ application.Render(0);
+ blendMode = actor.GetRendererAt(0u).GetProperty<int>( Renderer::Property::BLENDING_MODE );
+ DALI_TEST_EQUALS( static_cast<BlendingMode::Type>(blendMode), BlendingMode::ON, TEST_LOCATION );
+
END_TEST;
}
-
int UtcDaliRendererFactoryGetLinearGradientRenderer(void)
{
ToolkitTestApplication application;
END_TEST;
}
+
+int UtcDaliScrollViewSetGetProperty(void)
+{
+ ToolkitTestApplication application;
+
+ // Create the ScrollView actor
+ ScrollView scrollView = ScrollView::New();
+ DALI_TEST_CHECK(scrollView);
+
+ // Event side properties
+
+ // Test "wrapEnabled" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("wrapEnabled") == ScrollView::Property::WRAP_ENABLED );
+ scrollView.SetProperty( ScrollView::Property::WRAP_ENABLED, true );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::WRAP_ENABLED).Get<bool>(), true, TEST_LOCATION );
+
+ // Test "panningEnabled" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("panningEnabled") == ScrollView::Property::PANNING_ENABLED );
+ scrollView.SetProperty( ScrollView::Property::PANNING_ENABLED, false );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::PANNING_ENABLED).Get<bool>(), false, TEST_LOCATION );
+
+ // Test "axisAutoLockEnabled" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("axisAutoLockEnabled") == ScrollView::Property::AXIS_AUTO_LOCK_ENABLED );
+ scrollView.SetProperty( ScrollView::Property::AXIS_AUTO_LOCK_ENABLED, false );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::AXIS_AUTO_LOCK_ENABLED).Get<bool>(), false, TEST_LOCATION );
+
+ // Test "wheelScrollDistanceStep" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("wheelScrollDistanceStep") == ScrollView::Property::WHEEL_SCROLL_DISTANCE_STEP );
+ scrollView.SetProperty( ScrollView::Property::WHEEL_SCROLL_DISTANCE_STEP, Vector2(100.0f, 50.0f) );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::WHEEL_SCROLL_DISTANCE_STEP).Get<Vector2>(), Vector2(100.0f, 50.0f), TEST_LOCATION );
+
+ // Test "overshootEnabled" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("overshootEnabled") == Scrollable::Property::OVERSHOOT_ENABLED );
+ DALI_TEST_EQUALS( scrollView.GetProperty(Scrollable::Property::OVERSHOOT_ENABLED).Get<bool>(), scrollView.IsOvershootEnabled(), TEST_LOCATION );
+ scrollView.SetProperty( Scrollable::Property::OVERSHOOT_ENABLED, false );
+ DALI_TEST_EQUALS( scrollView.GetProperty(Scrollable::Property::OVERSHOOT_ENABLED).Get<bool>(), false, TEST_LOCATION );
+
+ // Animatable properties
+
+ // Test "scrollPosition" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPosition") == ScrollView::Property::SCROLL_POSITION );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_POSITION, Vector2(320.0f, 550.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_POSITION).Get<Vector2>(), Vector2(320.0f, 550.0f), TEST_LOCATION );
+
+ // Test "scrollPrePosition", "scrollPrePositionX" and "scrollPrePositionY" properties
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPrePosition") == ScrollView::Property::SCROLL_PRE_POSITION );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_PRE_POSITION, Vector2(300.0f, 500.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION).Get<Vector2>(), Vector2(300.0f, 500.0f), TEST_LOCATION );
+
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPrePositionX") == ScrollView::Property::SCROLL_PRE_POSITION_X );
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPrePositionY") == ScrollView::Property::SCROLL_PRE_POSITION_Y );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_X).Get<float>(), 300.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_Y).Get<float>(), 500.0f, TEST_LOCATION );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_PRE_POSITION_X, 400.0f );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_PRE_POSITION_Y, 600.0f );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_X).Get<float>(), 400.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_Y).Get<float>(), 600.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION).Get<Vector2>(), Vector2(400.0f, 600.0f), TEST_LOCATION );
+
+ // Test "scrollPrePositionMax", "scrollPrePositionMaxX" and "scrollPrePositionMaxY" properties
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPrePositionMax") == ScrollView::Property::SCROLL_PRE_POSITION_MAX );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_PRE_POSITION_MAX, Vector2(100.0f, 200.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_MAX).Get<Vector2>(), Vector2(100.0f, 200.0f), TEST_LOCATION );
+
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPrePositionMaxX") == ScrollView::Property::SCROLL_PRE_POSITION_MAX_X );
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPrePositionMaxY") == ScrollView::Property::SCROLL_PRE_POSITION_MAX_Y );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_MAX_X).Get<float>(), 100.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_MAX_Y).Get<float>(), 200.0f, TEST_LOCATION );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_PRE_POSITION_MAX_X, 300.0f );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_PRE_POSITION_MAX_Y, 400.0f );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_MAX_X).Get<float>(), 300.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_MAX_Y).Get<float>(), 400.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_PRE_POSITION_MAX).Get<Vector2>(), Vector2(300.0f, 400.0f), TEST_LOCATION );
+
+ // Test "overshootX" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("overshootX") == ScrollView::Property::OVERSHOOT_X );
+ scrollView.SetProperty( ScrollView::Property::OVERSHOOT_X, 0.8f );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::OVERSHOOT_X).Get<float>(), 0.8f, TEST_LOCATION );
+
+ // Test "overshootY" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("overshootY") == ScrollView::Property::OVERSHOOT_Y );
+ scrollView.SetProperty( ScrollView::Property::OVERSHOOT_Y, 0.8f );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::OVERSHOOT_Y).Get<float>(), 0.8f, TEST_LOCATION );
+
+ // Test "scrollFinal", "scrollFinalX" and "scrollFinalY" properties
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollFinal") == ScrollView::Property::SCROLL_FINAL );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_FINAL, Vector2(200.0f, 300.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_FINAL).Get<Vector2>(), Vector2(200.0f, 300.0f), TEST_LOCATION );
+
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollFinalX") == ScrollView::Property::SCROLL_FINAL_X );
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollFinalY") == ScrollView::Property::SCROLL_FINAL_Y );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_FINAL_X).Get<float>(), 200.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_FINAL_Y).Get<float>(), 300.0f, TEST_LOCATION );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_FINAL_X, 500.0f );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_FINAL_Y, 600.0f );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_FINAL_X).Get<float>(), 500.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_FINAL_Y).Get<float>(), 600.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_FINAL).Get<Vector2>(), Vector2(500.0f, 600.0f), TEST_LOCATION );
+
+ // Test "wrap" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("wrap") == ScrollView::Property::WRAP );
+ scrollView.SetProperty( ScrollView::Property::WRAP, false );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::WRAP).Get<bool>(), false, TEST_LOCATION );
+
+ // Test "panning" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("panning") == ScrollView::Property::PANNING );
+ scrollView.SetProperty( ScrollView::Property::PANNING, true );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::PANNING).Get<bool>(), true, TEST_LOCATION );
+
+ // Test "scrolling" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrolling") == ScrollView::Property::SCROLLING );
+ scrollView.SetProperty( ScrollView::Property::SCROLLING, false );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLLING).Get<bool>(), false, TEST_LOCATION );
+
+ // Test "scrollDomainSize", "scrollDomainSizeX" and "scrollDomainSizeY" properties
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollDomainSize") == ScrollView::Property::SCROLL_DOMAIN_SIZE );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_DOMAIN_SIZE, Vector2(1200.0f, 1300.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_SIZE).Get<Vector2>(), Vector2(1200.0f, 1300.0f), TEST_LOCATION );
+
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollDomainSizeX") == ScrollView::Property::SCROLL_DOMAIN_SIZE_X );
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollDomainSizeY") == ScrollView::Property::SCROLL_DOMAIN_SIZE_Y );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_SIZE_X).Get<float>(), 1200.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_SIZE_Y).Get<float>(), 1300.0f, TEST_LOCATION );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_DOMAIN_SIZE_X, 1500.0f );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_DOMAIN_SIZE_Y, 1600.0f );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_SIZE_X).Get<float>(), 1500.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_SIZE_Y).Get<float>(), 1600.0f, TEST_LOCATION );
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_SIZE).Get<Vector2>(), Vector2(1500.0f, 1600.0f), TEST_LOCATION );
+
+ // Test "scrollDomainOffset" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollDomainOffset") == ScrollView::Property::SCROLL_DOMAIN_OFFSET );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_DOMAIN_OFFSET, Vector2(500.0f, 200.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_DOMAIN_OFFSET).Get<Vector2>(), Vector2(500.0f, 200.0f), TEST_LOCATION );
+
+ // Test "scrollPositionDelta" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("scrollPositionDelta") == ScrollView::Property::SCROLL_POSITION_DELTA );
+ scrollView.SetProperty( ScrollView::Property::SCROLL_POSITION_DELTA, Vector2(10.0f, 30.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::SCROLL_POSITION_DELTA).Get<Vector2>(), Vector2(10.0f, 30.0f), TEST_LOCATION );
+
+ // Test "startPagePosition" property
+ DALI_TEST_CHECK( scrollView.GetPropertyIndex("startPagePosition") == ScrollView::Property::START_PAGE_POSITION );
+ scrollView.SetProperty( ScrollView::Property::START_PAGE_POSITION, Vector3(50.0f, 100.0f, 20.0f) );
+ Wait(application);
+ DALI_TEST_EQUALS( scrollView.GetProperty(ScrollView::Property::START_PAGE_POSITION).Get<Vector3>(), Vector3(50.0f, 100.0f, 20.0f), TEST_LOCATION );
+
+ END_TEST;
+}
--- /dev/null
+/*
+ * Copyright (c) 2016 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/devel-api/rendering/renderer.h>
+#include <dali/integration-api/events/key-event-integ.h>
+#include <dali/integration-api/events/tap-gesture-event.h>
+#include <dali-toolkit-test-suite-utils.h>
+#include <dali-toolkit/dali-toolkit.h>
+#include <dali-toolkit/devel-api/controls/text-controls/text-editor.h> ///< @todo to be removed when text-editor is added to the dali-toolkit.h
+#include <dali-toolkit/devel-api/styling/style-manager.h>
+
+using namespace Dali;
+using namespace Toolkit;
+
+void dali_texteditor_startup(void)
+{
+ test_return_value = TET_UNDEF;
+}
+
+void dali_texteditor_cleanup(void)
+{
+ test_return_value = TET_PASS;
+}
+
+namespace
+{
+
+const char* const PROPERTY_NAME_RENDERING_BACKEND = "renderingBackend";
+const char* const PROPERTY_NAME_TEXT = "text";
+const char* const PROPERTY_NAME_TEXT_COLOR = "textColor";
+const char* const PROPERTY_NAME_FONT_FAMILY = "fontFamily";
+const char* const PROPERTY_NAME_FONT_STYLE = "fontStyle";
+const char* const PROPERTY_NAME_POINT_SIZE = "pointSize";
+const char* const PROPERTY_NAME_HORIZONTAL_ALIGNMENT = "horizontalAlignment";
+const char* const PROPERTY_NAME_SCROLL_THRESHOLD = "scrollThreshold";
+const char* const PROPERTY_NAME_SCROLL_SPEED = "scrollSpeed";
+const char* const PROPERTY_NAME_PRIMARY_CURSOR_COLOR = "primaryCursorColor";
+const char* const PROPERTY_NAME_SECONDARY_CURSOR_COLOR = "secondaryCursorColor";
+const char* const PROPERTY_NAME_ENABLE_CURSOR_BLINK = "enableCursorBlink";
+const char* const PROPERTY_NAME_CURSOR_BLINK_INTERVAL = "cursorBlinkInterval";
+const char* const PROPERTY_NAME_CURSOR_BLINK_DURATION = "cursorBlinkDuration";
+const char* const PROPERTY_NAME_CURSOR_WIDTH = "cursorWidth";
+const char* const PROPERTY_NAME_GRAB_HANDLE_IMAGE = "grabHandleImage";
+const char* const PROPERTY_NAME_GRAB_HANDLE_PRESSED_IMAGE = "grabHandlePressedImage";
+const char* const PROPERTY_NAME_SELECTION_HANDLE_IMAGE_LEFT = "selectionHandleImageLeft";
+const char* const PROPERTY_NAME_SELECTION_HANDLE_IMAGE_RIGHT = "selectionHandleImageRight";
+const char* const PROPERTY_NAME_SELECTION_HANDLE_PRESSED_IMAGE_LEFT = "selectionHandlePressedImageLeft";
+const char* const PROPERTY_NAME_SELECTION_HANDLE_PRESSED_IMAGE_RIGHT = "selectionHandlePressedImageRight";
+const char* const PROPERTY_NAME_SELECTION_HANDLE_MARKER_IMAGE_LEFT = "selectionHandleMarkerImageLeft";
+const char* const PROPERTY_NAME_SELECTION_HANDLE_MARKER_IMAGE_RIGHT = "selectionHandleMarkerImageRight";
+const char* const PROPERTY_NAME_SELECTION_HIGHLIGHT_COLOR = "selectionHighlightColor";
+const char* const PROPERTY_NAME_DECORATION_BOUNDING_BOX = "decorationBoundingBox";
+const char* const PROPERTY_NAME_ENABLE_MARKUP = "enableMarkup";
+const char* const PROPERTY_NAME_INPUT_COLOR = "inputColor";
+const char* const PROPERTY_NAME_INPUT_FONT_FAMILY = "inputFontFamily";
+const char* const PROPERTY_NAME_INPUT_FONT_STYLE = "inputFontStyle";
+const char* const PROPERTY_NAME_INPUT_POINT_SIZE = "inputPointSize";
+
+const int DEFAULT_RENDERING_BACKEND = Dali::Toolkit::Text::DEFAULT_RENDERING_BACKEND;
+
+const Dali::Vector4 LIGHT_BLUE( 0.75f, 0.96f, 1.f, 1.f ); // The text highlight color.
+
+const unsigned int CURSOR_BLINK_INTERVAL = 500u; // Cursor blink interval
+const float TO_MILLISECONDS = 1000.f;
+const float TO_SECONDS = 1.f / TO_MILLISECONDS;
+
+const float SCROLL_THRESHOLD = 10.f;
+const float SCROLL_SPEED = 300.f;
+
+static bool gTextChangedCallBackCalled;
+
+static void TestTextChangedCallback( TextEditor control )
+{
+ tet_infoline(" TestTextChangedCallback");
+
+ gTextChangedCallBackCalled = true;
+}
+
+// Generate a TapGestureEvent to send to Core.
+Integration::TapGestureEvent GenerateTap(
+ Gesture::State state,
+ unsigned int numberOfTaps,
+ unsigned int numberOfTouches,
+ Vector2 point)
+{
+ Integration::TapGestureEvent tap( state );
+
+ tap.numberOfTaps = numberOfTaps;
+ tap.numberOfTouches = numberOfTouches;
+ tap.point = point;
+
+ return tap;
+}
+
+// Generate a KeyEvent to send to Core.
+Integration::KeyEvent GenerateKey( const std::string& keyName,
+ const std::string& keyString,
+ int keyCode,
+ int keyModifier,
+ unsigned long timeStamp,
+ const Integration::KeyEvent::State& keyState )
+{
+ return Integration::KeyEvent( keyName,
+ keyString,
+ keyCode,
+ keyModifier,
+ timeStamp,
+ keyState );
+}
+
+} // namespace
+
+int UtcDaliToolkitTextEditorConstructorP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorConstructorP");
+ TextEditor textEditor;
+ DALI_TEST_CHECK( !textEditor );
+ END_TEST;
+}
+
+int UtcDaliToolkitTextEditorNewP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorNewP");
+ TextEditor textEditor = TextEditor::New();
+ DALI_TEST_CHECK( textEditor );
+ END_TEST;
+}
+
+int UtcDaliToolkitTextEditorDownCastP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorDownCastP");
+ TextEditor textEditor1 = TextEditor::New();
+ BaseHandle object( textEditor1 );
+
+ TextEditor textEditor2 = TextEditor::DownCast( object );
+ DALI_TEST_CHECK( textEditor2 );
+
+ TextEditor textEditor3 = DownCast< TextEditor >( object );
+ DALI_TEST_CHECK( textEditor3 );
+ END_TEST;
+}
+
+int UtcDaliToolkitTextEditorDownCastN(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorDownCastN");
+ BaseHandle uninitializedObject;
+ TextEditor textEditor1 = TextEditor::DownCast( uninitializedObject );
+ DALI_TEST_CHECK( !textEditor1 );
+
+ TextEditor textEditor2 = DownCast< TextEditor >( uninitializedObject );
+ DALI_TEST_CHECK( !textEditor2 );
+ END_TEST;
+}
+
+int UtcDaliToolkitTextEditorCopyConstructorP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorCopyConstructorP");
+ TextEditor textEditor = TextEditor::New();
+ textEditor.SetProperty( TextEditor::Property::TEXT, "Test" );
+
+ TextEditor copy( textEditor );
+ DALI_TEST_CHECK( copy );
+ DALI_TEST_CHECK( copy.GetProperty<std::string>( TextLabel::Property::TEXT ) == textEditor.GetProperty<std::string>( TextLabel::Property::TEXT ) );
+ END_TEST;
+}
+
+int UtcDaliToolkitTextEditorAssignmentOperatorP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorAssignmentOperatorP");
+ TextEditor textEditor = TextEditor::New();
+ textEditor.SetProperty( TextEditor::Property::TEXT, "Test" );
+
+ TextEditor copy = textEditor;
+ DALI_TEST_CHECK( copy );
+ DALI_TEST_CHECK( copy.GetProperty<std::string>( TextEditor::Property::TEXT ) == textEditor.GetProperty<std::string>( TextEditor::Property::TEXT ) );
+ END_TEST;
+}
+
+int UtcDaliTextEditorNewP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorNewP");
+ TextEditor textEditor = TextEditor::New();
+ DALI_TEST_CHECK( textEditor );
+ END_TEST;
+}
+
+// Positive test case for a method
+int UtcDaliTextEditorGetPropertyP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorGetPropertyP");
+ TextEditor editor = TextEditor::New();
+ DALI_TEST_CHECK( editor );
+
+ // Check Property Indices are correct
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_RENDERING_BACKEND ) == TextEditor::Property::RENDERING_BACKEND );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_TEXT ) == TextEditor::Property::TEXT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_TEXT_COLOR ) == TextEditor::Property::TEXT_COLOR );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_FONT_FAMILY ) == TextEditor::Property::FONT_FAMILY );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_FONT_STYLE ) == TextEditor::Property::FONT_STYLE );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_POINT_SIZE ) == TextEditor::Property::POINT_SIZE );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_HORIZONTAL_ALIGNMENT ) == TextEditor::Property::HORIZONTAL_ALIGNMENT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SCROLL_THRESHOLD ) == TextEditor::Property::SCROLL_THRESHOLD );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SCROLL_SPEED ) == TextEditor::Property::SCROLL_SPEED );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_PRIMARY_CURSOR_COLOR ) == TextEditor::Property::PRIMARY_CURSOR_COLOR );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SECONDARY_CURSOR_COLOR ) == TextEditor::Property::SECONDARY_CURSOR_COLOR );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_ENABLE_CURSOR_BLINK ) == TextEditor::Property::ENABLE_CURSOR_BLINK );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_CURSOR_BLINK_INTERVAL ) == TextEditor::Property::CURSOR_BLINK_INTERVAL );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_CURSOR_BLINK_DURATION ) == TextEditor::Property::CURSOR_BLINK_DURATION );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_CURSOR_WIDTH ) == TextEditor::Property::CURSOR_WIDTH );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_GRAB_HANDLE_IMAGE ) == TextEditor::Property::GRAB_HANDLE_IMAGE );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_GRAB_HANDLE_PRESSED_IMAGE ) == TextEditor::Property::GRAB_HANDLE_PRESSED_IMAGE );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HANDLE_IMAGE_LEFT ) == TextEditor::Property::SELECTION_HANDLE_IMAGE_LEFT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HANDLE_IMAGE_RIGHT ) == TextEditor::Property::SELECTION_HANDLE_IMAGE_RIGHT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HANDLE_PRESSED_IMAGE_LEFT ) == TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_LEFT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HANDLE_PRESSED_IMAGE_RIGHT ) == TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_RIGHT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HANDLE_MARKER_IMAGE_LEFT ) == TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_LEFT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HANDLE_MARKER_IMAGE_RIGHT ) == TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_RIGHT );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_SELECTION_HIGHLIGHT_COLOR ) == TextEditor::Property::SELECTION_HIGHLIGHT_COLOR );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_DECORATION_BOUNDING_BOX ) == TextEditor::Property::DECORATION_BOUNDING_BOX );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_ENABLE_MARKUP ) == TextEditor::Property::ENABLE_MARKUP );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_INPUT_COLOR ) == TextEditor::Property::INPUT_COLOR );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_INPUT_FONT_FAMILY ) == TextEditor::Property::INPUT_FONT_FAMILY );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_INPUT_FONT_STYLE ) == TextEditor::Property::INPUT_FONT_STYLE );
+ DALI_TEST_CHECK( editor.GetPropertyIndex( PROPERTY_NAME_INPUT_POINT_SIZE ) == TextEditor::Property::INPUT_POINT_SIZE );
+ END_TEST;
+}
+
+bool SetPropertyMapRetrieved( TextEditor& editor, const Property::Index property, const std::string mapKey, const std::string mapValue )
+{
+ bool result = false;
+ Property::Map imageMap;
+ imageMap[mapKey] =mapValue;
+
+ editor.SetProperty( property , imageMap );
+ Property::Value propValue = editor.GetProperty( property );
+ Property::Map* resultMap = propValue.GetMap();
+
+ if ( resultMap->Find( mapKey )->Get< std::string>() == mapValue )
+ {
+ result = true;
+ }
+
+ return result;
+}
+
+// Positive test case for a method
+int UtcDaliTextEditorSetPropertyP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorSetPropertyP");
+ TextEditor editor = TextEditor::New();
+ DALI_TEST_CHECK( editor );
+ Stage::GetCurrent().Add( editor );
+
+ // Note - we can't check the defaults since the stylesheets are platform-specific
+
+ // Check the render backend property.
+ editor.SetProperty( TextEditor::Property::RENDERING_BACKEND, Text::RENDERING_SHARED_ATLAS );
+ DALI_TEST_EQUALS( (Text::RenderingType)editor.GetProperty<int>( TextEditor::Property::RENDERING_BACKEND ), Text::RENDERING_SHARED_ATLAS, TEST_LOCATION );
+
+ // Check text property.
+ editor.SetProperty( TextEditor::Property::TEXT, "Setting Text" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::TEXT ), std::string("Setting Text"), TEST_LOCATION );
+
+ // Check text's color property
+ editor.SetProperty( TextEditor::Property::TEXT_COLOR, Color::WHITE );
+ DALI_TEST_EQUALS( editor.GetProperty<Vector4>( TextEditor::Property::TEXT_COLOR ), Color::WHITE, TEST_LOCATION );
+
+ // Check font properties.
+ editor.SetProperty( TextEditor::Property::FONT_FAMILY, "Setting font family" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::FONT_FAMILY ), std::string("Setting font family"), TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::FONT_STYLE, "Setting font style" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::FONT_STYLE ), std::string("Setting font style"), TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::POINT_SIZE, 10.f );
+ DALI_TEST_EQUALS( editor.GetProperty<float>( TextEditor::Property::POINT_SIZE ), 10.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+
+ // Check that the Alignment properties can be correctly set
+ editor.SetProperty( TextEditor::Property::HORIZONTAL_ALIGNMENT, "END" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::HORIZONTAL_ALIGNMENT ), "END", TEST_LOCATION );
+
+ // Check scroll properties.
+ editor.SetProperty( TextEditor::Property::SCROLL_THRESHOLD, 1.f );
+ DALI_TEST_EQUALS( editor.GetProperty<float>( TextEditor::Property::SCROLL_THRESHOLD ), 1.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::SCROLL_SPEED, 100.f );
+ DALI_TEST_EQUALS( editor.GetProperty<float>( TextEditor::Property::SCROLL_SPEED ), 100.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+
+ // Check cursor properties
+ editor.SetProperty( TextEditor::Property::PRIMARY_CURSOR_COLOR, Color::RED );
+ DALI_TEST_EQUALS( editor.GetProperty<Vector4>( TextEditor::Property::PRIMARY_CURSOR_COLOR ), Color::RED, TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::SECONDARY_CURSOR_COLOR, Color::BLUE );
+ DALI_TEST_EQUALS( editor.GetProperty<Vector4>( TextEditor::Property::SECONDARY_CURSOR_COLOR ), Color::BLUE, TEST_LOCATION );
+
+ editor.SetProperty( TextEditor::Property::ENABLE_CURSOR_BLINK, false );
+ DALI_TEST_EQUALS( editor.GetProperty<bool>( TextEditor::Property::ENABLE_CURSOR_BLINK ), false, TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::CURSOR_BLINK_INTERVAL, 1.f );
+ DALI_TEST_EQUALS( editor.GetProperty<float>( TextEditor::Property::CURSOR_BLINK_INTERVAL ), 1.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::CURSOR_BLINK_DURATION, 10.f );
+ DALI_TEST_EQUALS( editor.GetProperty<float>( TextEditor::Property::CURSOR_BLINK_DURATION ), 10.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::CURSOR_WIDTH, 1 );
+ DALI_TEST_EQUALS( editor.GetProperty<int>( TextEditor::Property::CURSOR_WIDTH ), 1, TEST_LOCATION );
+
+ // Check handle images
+ editor.SetProperty( TextEditor::Property::GRAB_HANDLE_IMAGE, "image1" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::GRAB_HANDLE_IMAGE ), "image1", TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::GRAB_HANDLE_PRESSED_IMAGE, "image2" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::GRAB_HANDLE_PRESSED_IMAGE ), "image2", TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::SELECTION_HANDLE_IMAGE_LEFT, "image3" );
+
+ // Check handle images
+ DALI_TEST_CHECK( SetPropertyMapRetrieved( editor, TextEditor::Property::SELECTION_HANDLE_IMAGE_LEFT, "filename", "leftHandleImage" ) );
+ DALI_TEST_CHECK( SetPropertyMapRetrieved( editor, TextEditor::Property::SELECTION_HANDLE_IMAGE_RIGHT, "filename", "rightHandleImage" ) );
+ DALI_TEST_CHECK( SetPropertyMapRetrieved( editor, TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_LEFT, "filename", "leftHandleImagePressed" ) );
+ DALI_TEST_CHECK( SetPropertyMapRetrieved( editor, TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_RIGHT, "filename", "rightHandleImagePressed" ) );
+ DALI_TEST_CHECK( SetPropertyMapRetrieved( editor, TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_LEFT, "filename", "leftHandleMarkerImage" ) );
+ DALI_TEST_CHECK( SetPropertyMapRetrieved( editor, TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_RIGHT, "filename", "rightHandleMarkerImage" ) );
+
+ // Check the highlight color
+ editor.SetProperty( TextEditor::Property::SELECTION_HIGHLIGHT_COLOR, Color::GREEN );
+ DALI_TEST_EQUALS( editor.GetProperty<Vector4>( TextEditor::Property::SELECTION_HIGHLIGHT_COLOR ), Color::GREEN, TEST_LOCATION );
+
+ // Decoration bounding box
+ editor.SetProperty( TextEditor::Property::DECORATION_BOUNDING_BOX, Rect<int>( 0, 0, 1, 1 ) );
+ DALI_TEST_EQUALS( editor.GetProperty<Rect <int > >( TextEditor::Property::DECORATION_BOUNDING_BOX ), Rect<int>( 0, 0, 1, 1 ), TEST_LOCATION );
+
+ // Check the enable markup property.
+ DALI_TEST_CHECK( !editor.GetProperty<bool>( TextEditor::Property::ENABLE_MARKUP ) );
+ editor.SetProperty( TextEditor::Property::ENABLE_MARKUP, true );
+ DALI_TEST_CHECK( editor.GetProperty<bool>( TextEditor::Property::ENABLE_MARKUP ) );
+
+ // Check input color property.
+ editor.SetProperty( TextEditor::Property::INPUT_COLOR, Color::YELLOW );
+ DALI_TEST_EQUALS( editor.GetProperty<Vector4>( TextEditor::Property::INPUT_COLOR ), Color::YELLOW, TEST_LOCATION );
+
+ // Check input font properties.
+ editor.SetProperty( TextEditor::Property::INPUT_FONT_FAMILY, "Setting input font family" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::INPUT_FONT_FAMILY ), "Setting input font family", TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::INPUT_FONT_STYLE, "Setting input font style" );
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::INPUT_FONT_STYLE ), "Setting input font style", TEST_LOCATION );
+ editor.SetProperty( TextEditor::Property::INPUT_POINT_SIZE, 12.f );
+ DALI_TEST_EQUALS( editor.GetProperty<float>( TextEditor::Property::INPUT_POINT_SIZE ), 12.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+
+ END_TEST;
+}
+
+// Positive Atlas Text Renderer test
+int utcDaliTextEditorAtlasRenderP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" UtcDaliToolkitTextEditorAtlasRenderP");
+ StyleManager styleManager = StyleManager::Get();
+ styleManager.RequestDefaultTheme();
+ TextEditor editor = TextEditor::New();
+ DALI_TEST_CHECK( editor );
+
+ editor.SetProperty( TextEditor::Property::HORIZONTAL_ALIGNMENT, "CENTER" );
+
+ application.GetGlAbstraction().SetCheckFramebufferStatusResult( GL_FRAMEBUFFER_COMPLETE );
+
+ Stage::GetCurrent().Add( editor );
+
+ try
+ {
+ // Render some text with the shared atlas backend
+ editor.SetProperty( TextEditor::Property::RENDERING_BACKEND, Text::RENDERING_SHARED_ATLAS );
+ application.SendNotification();
+ application.Render();
+ }
+ catch( ... )
+ {
+ tet_result(TET_FAIL);
+ }
+ END_TEST;
+}
+
+// Positive test for the textChanged signal.
+int utcDaliTextEditorTextChangedP(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" utcDaliTextEditorTextChangedP");
+ TextEditor editor = TextEditor::New();
+ DALI_TEST_CHECK( editor );
+
+ Stage::GetCurrent().Add( editor );
+
+ editor.TextChangedSignal().Connect(&TestTextChangedCallback);
+
+ gTextChangedCallBackCalled = false;
+ editor.SetProperty( TextEditor::Property::TEXT, "ABC" );
+ DALI_TEST_CHECK( gTextChangedCallBackCalled );
+
+ application.SendNotification();
+
+ editor.SetKeyInputFocus();
+
+ gTextChangedCallBackCalled = false;
+ application.ProcessEvent( GenerateKey( "D", "D", 0, 0, 0, Integration::KeyEvent::Down ) );
+ DALI_TEST_CHECK( gTextChangedCallBackCalled );
+
+ END_TEST;
+}
+
+int utcDaliTextEditorEvent01(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" utcDaliTextEditorEvent01");
+
+ // Creates a tap event. After creating a tap event the text editor should
+ // have the focus and add text with key events should be possible.
+
+ TextEditor editor = TextEditor::New();
+ DALI_TEST_CHECK( editor );
+
+ Stage::GetCurrent().Add( editor );
+
+ editor.SetSize( 300.f, 50.f );
+ editor.SetParentOrigin( ParentOrigin::TOP_LEFT );
+ editor.SetAnchorPoint( AnchorPoint::TOP_LEFT );
+
+ // Avoid a crash when core load gl resources.
+ application.GetGlAbstraction().SetCheckFramebufferStatusResult( GL_FRAMEBUFFER_COMPLETE );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Add a key event but as the text editor has not the focus it should do nothing.
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::TEXT ), std::string(""), TEST_LOCATION );
+
+ // Create a tap event to touch the text editor.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 150.0f, 25.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 150.0f, 25.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Now the text editor has the focus, so it can handle the key events.
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_EQUALS( editor.GetProperty<std::string>( TextEditor::Property::TEXT ), std::string("aa"), TEST_LOCATION );
+
+ // Create a second text editor and send key events to it.
+ TextEditor editor2 = TextEditor::New();
+
+ editor2.SetParentOrigin( ParentOrigin::TOP_LEFT );
+ editor2.SetAnchorPoint( AnchorPoint::TOP_LEFT );
+ editor2.SetSize( 100.f, 100.f );
+ editor2.SetPosition( 100.f, 100.f );
+
+ Stage::GetCurrent().Add( editor2 );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Create a tap event on the second text editor.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 150.0f, 125.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 150.0f, 125.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // The second text editor has the focus. It should handle the key events.
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Check the text has been added to the second text editor.
+ DALI_TEST_EQUALS( editor2.GetProperty<std::string>( TextEditor::Property::TEXT ), std::string("aa"), TEST_LOCATION );
+
+ END_TEST;
+}
+
+int utcDaliTextEditorEvent02(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" utcDaliTextEditorEvent02");
+
+ // Checks if the right number of actors are created.
+
+ TextEditor editor = TextEditor::New();
+ editor.SetProperty( TextEditor::Property::POINT_SIZE, 10.f );
+ DALI_TEST_CHECK( editor );
+
+ Stage::GetCurrent().Add( editor );
+
+ editor.SetSize( 300.f, 50.f );
+ editor.SetParentOrigin( ParentOrigin::TOP_LEFT );
+ editor.SetAnchorPoint( AnchorPoint::TOP_LEFT );
+
+ // Avoid a crash when core load gl resources.
+ application.GetGlAbstraction().SetCheckFramebufferStatusResult( GL_FRAMEBUFFER_COMPLETE );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Check there are the expected number of children ( active layer, offscreen root actor, and the offscreen image actor
+ DALI_TEST_EQUALS( editor.GetChildCount(), 3u, TEST_LOCATION );
+
+ Actor layer = editor.GetChildAt( 0u );
+ DALI_TEST_CHECK( layer.IsLayer() );
+
+ Actor offscreenRoot = editor.GetChildAt( 1u );
+ DALI_TEST_CHECK( offscreenRoot.IsLayer() );
+ DALI_TEST_EQUALS( offscreenRoot.GetChildCount(), 1u, TEST_LOCATION ); // The camera actor.
+
+ Actor offscreenImage = editor.GetChildAt( 2u );
+ ImageActor imageActor = ImageActor::DownCast( offscreenImage );
+ DALI_TEST_CHECK( imageActor );
+
+ // Create a tap event to touch the text editor.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 150.0f, 25.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 150.0f, 25.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_EQUALS( layer.GetChildCount(), 1u, TEST_LOCATION ); // The cursor.
+ DALI_TEST_EQUALS( offscreenRoot.GetChildCount(), 1u, TEST_LOCATION ); // The camera actor.
+
+ // Now the text editor has the focus, so it can handle the key events.
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+ application.ProcessEvent( GenerateKey( "a", "a", 0, 0, 0, Integration::KeyEvent::Down ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Checks the cursor and the renderer have been created.
+ DALI_TEST_EQUALS( layer.GetChildCount(), 1u, TEST_LOCATION ); // The cursor.
+ DALI_TEST_EQUALS( offscreenRoot.GetChildCount(), 2u, TEST_LOCATION ); // The camera actor and the renderer
+
+ Control cursor = Control::DownCast( layer.GetChildAt( 0u ) );
+ DALI_TEST_CHECK( cursor );
+
+ CameraActor camera = CameraActor::DownCast( offscreenRoot.GetChildAt( 0u ) );
+ DALI_TEST_CHECK( camera );
+
+ Renderer renderer = offscreenRoot.GetChildAt( 1u ).GetRendererAt( 0u );
+ DALI_TEST_CHECK( renderer );
+
+ // Move the cursor and check the position changes.
+ Vector3 position1 = cursor.GetCurrentPosition();
+
+ application.ProcessEvent( GenerateKey( "", "", DALI_KEY_CURSOR_LEFT, 0, 0, Integration::KeyEvent::Down ) );
+ application.ProcessEvent( GenerateKey( "", "", DALI_KEY_CURSOR_LEFT, 0, 0, Integration::KeyEvent::Down ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ Vector3 position2 = cursor.GetCurrentPosition();
+
+ DALI_TEST_CHECK( position2.x < position1.x );
+
+ application.ProcessEvent( GenerateKey( "", "", DALI_KEY_CURSOR_RIGHT, 0, 0, Integration::KeyEvent::Down ) );
+ application.ProcessEvent( GenerateKey( "", "", DALI_KEY_CURSOR_RIGHT, 0, 0, Integration::KeyEvent::Down ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ Vector3 position3 = cursor.GetCurrentPosition();
+
+ DALI_TEST_EQUALS( position1, position3, TEST_LOCATION ); // Should be in the same position1.
+
+ // Send some taps and check the cursor positions.
+
+ // Try to tap at the beginning.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 1.f, 25.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 1.f, 25.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Cursor position should be the same than position1.
+ Vector3 position4 = cursor.GetCurrentPosition();
+
+ DALI_TEST_EQUALS( position2, position4, TEST_LOCATION ); // Should be in the same position2.
+
+ // Tap away from the start position.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 16.f, 25.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 16.0f, 25.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ Vector3 position5 = cursor.GetCurrentPosition();
+
+ DALI_TEST_CHECK( position5.x > position4.x );
+
+ // Remove all the text.
+ application.ProcessEvent( GenerateKey( "", "", DALI_KEY_BACKSPACE, 0, 0, Integration::KeyEvent::Down ) );
+ application.ProcessEvent( GenerateKey( "", "", DALI_KEY_BACKSPACE, 0, 0, Integration::KeyEvent::Down ) );
+ editor.SetProperty( TextEditor::Property::TEXT, "" );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Cursor position should be the same than position2.
+ Vector3 position6 = cursor.GetCurrentPosition();
+
+ DALI_TEST_EQUALS( position2, position6, TEST_LOCATION );// Should be in the same position2.
+
+ // Should not be a renderer.
+ DALI_TEST_EQUALS( offscreenRoot.GetChildCount(), 1u, TEST_LOCATION ); // The camera actor only.
+
+ END_TEST;
+}
+
+int utcDaliTextEditorEvent03(void)
+{
+ ToolkitTestApplication application;
+ tet_infoline(" utcDaliTextEditorEvent03");
+
+ // Checks if the highlight actor is created.
+
+ TextEditor editor = TextEditor::New();
+ DALI_TEST_CHECK( editor );
+
+ Stage::GetCurrent().Add( editor );
+
+ editor.SetProperty( TextEditor::Property::TEXT, "This is a long text for the size of the text-editor." );
+ editor.SetProperty( TextEditor::Property::POINT_SIZE, 10.f );
+ editor.SetSize( 30.f, 50.f );
+ editor.SetParentOrigin( ParentOrigin::TOP_LEFT );
+ editor.SetAnchorPoint( AnchorPoint::TOP_LEFT );
+
+ // Avoid a crash when core load gl resources.
+ application.GetGlAbstraction().SetCheckFramebufferStatusResult( GL_FRAMEBUFFER_COMPLETE );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Tap first to get the focus.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 3.f, 25.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 3.f, 25.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // Double tap to select a word.
+ application.ProcessEvent( GenerateTap( Gesture::Possible, 2u, 1u, Vector2( 3.f, 25.0f ) ) );
+ application.ProcessEvent( GenerateTap( Gesture::Started, 2u, 1u, Vector2( 3.f, 25.0f ) ) );
+
+ // Render and notify
+ application.SendNotification();
+ application.Render();
+
+ // The offscreen root actor should have three actors: the camera, a renderer and the highlight actor.
+ Actor offscreenRoot = editor.GetChildAt( 1u );
+ DALI_TEST_CHECK( offscreenRoot.IsLayer() );
+
+ CameraActor camera = CameraActor::DownCast( offscreenRoot.GetChildAt( 0u ) );
+ DALI_TEST_CHECK( camera );
+
+ Renderer renderer = offscreenRoot.GetChildAt( 1u ).GetRendererAt( 0u );
+ DALI_TEST_CHECK( renderer );
+
+ Renderer highlight = offscreenRoot.GetChildAt( 2u ).GetRendererAt( 0u );
+ DALI_TEST_CHECK( highlight );
+
+ END_TEST;
+}
const char* const PROPERTY_NAME_INPUT_METHOD_SETTINGS = "inputMethodSettings";
const char* const PROPERTY_NAME_INPUT_COLOR = "inputColor";
const char* const PROPERTY_NAME_ENABLE_MARKUP = "enableMarkup";
+const char* const PROPERTY_NAME_INPUT_FONT_FAMILY = "inputFontFamily";
+const char* const PROPERTY_NAME_INPUT_FONT_STYLE = "inputFontStyle";
+const char* const PROPERTY_NAME_INPUT_POINT_SIZE = "inputPointSize";
const int DEFAULT_RENDERING_BACKEND = Dali::Toolkit::Text::DEFAULT_RENDERING_BACKEND;
DALI_TEST_CHECK( field.GetPropertyIndex( PROPERTY_NAME_INPUT_METHOD_SETTINGS ) == TextField::Property::INPUT_METHOD_SETTINGS );
DALI_TEST_CHECK( field.GetPropertyIndex( PROPERTY_NAME_INPUT_COLOR ) == TextField::Property::INPUT_COLOR );
DALI_TEST_CHECK( field.GetPropertyIndex( PROPERTY_NAME_ENABLE_MARKUP ) == TextField::Property::ENABLE_MARKUP );
+ DALI_TEST_CHECK( field.GetPropertyIndex( PROPERTY_NAME_INPUT_FONT_FAMILY ) == TextField::Property::INPUT_FONT_FAMILY );
+ DALI_TEST_CHECK( field.GetPropertyIndex( PROPERTY_NAME_INPUT_FONT_STYLE ) == TextField::Property::INPUT_FONT_STYLE );
+ DALI_TEST_CHECK( field.GetPropertyIndex( PROPERTY_NAME_INPUT_POINT_SIZE ) == TextField::Property::INPUT_POINT_SIZE );
END_TEST;
}
field.SetProperty( TextField::Property::DECORATION_BOUNDING_BOX, Rect<int>( 0, 0, 1, 1 ) );
DALI_TEST_EQUALS( field.GetProperty<Rect <int > >( TextField::Property::DECORATION_BOUNDING_BOX ), Rect<int>( 0, 0, 1, 1 ), TEST_LOCATION );
- // Input color
+ // Check input color property.
field.SetProperty( TextField::Property::INPUT_COLOR, Color::YELLOW );
DALI_TEST_EQUALS( field.GetProperty<Vector4>( TextField::Property::INPUT_COLOR ), Color::YELLOW, TEST_LOCATION );
field.SetProperty( TextField::Property::ENABLE_MARKUP, true );
DALI_TEST_CHECK( field.GetProperty<bool>( TextField::Property::ENABLE_MARKUP ) );
+ // Check input font properties.
+ field.SetProperty( TextField::Property::INPUT_FONT_FAMILY, "Setting input font family" );
+ DALI_TEST_EQUALS( field.GetProperty<std::string>( TextField::Property::INPUT_FONT_FAMILY ), "Setting input font family", TEST_LOCATION );
+ field.SetProperty( TextField::Property::INPUT_FONT_STYLE, "Setting input font style" );
+ DALI_TEST_EQUALS( field.GetProperty<std::string>( TextField::Property::INPUT_FONT_STYLE ), "Setting input font style", TEST_LOCATION );
+ field.SetProperty( TextField::Property::INPUT_POINT_SIZE, 12.f );
+ DALI_TEST_EQUALS( field.GetProperty<float>( TextField::Property::INPUT_POINT_SIZE ), 12.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
+
END_TEST;
}
AC_SUBST(DALI_TOOLKIT_VERSION)
PKG_CHECK_MODULES(DALICORE, dali-core)
-PKG_CHECK_MODULES(DALI, dali)
DALI_TOOLKIT_CFLAGS=-DPLATFORM_TIZEN
-I../../../ \
$(DALI_TOOLKIT_CFLAGS) \
$(DALICORE_CFLAGS) \
- $(DALI_CFLAGS) \
$(DLOG_CFLAGS) \
$(FRIBIDI_CFLAGS) \
$(HTMLCXX_CFLAGS)
libdali_toolkit_la_LIBADD = \
$(DALICORE_LIBS) \
- $(DALI_LIBS) \
$(DLOG_LIBS) \
$(FRIBIDI_LIBS) \
$(HTMLCXX_LIBS)
develapitextselectionpopupdir = $(develapicontrolsdir)/text-controls
# devel headers
+develapicontrols_HEADERS = $(devel_api_controls_header_files)
develapibloomview_HEADERS = $(devel_api_bloom_view_header_files)
develapibubbleemitter_HEADERS = $(devel_api_bubble_emitter_header_files)
develapibuilder_HEADERS = $(devel_api_builder_header_files)
develapitextselectionpopup_HEADERS = $(devel_api_text_controls_header_files)
# public api source
-publicapidir = $(topleveldir)/public-api
-publicapicontrolsdir = $(publicapidir)/controls
-develapiaccessibilitymanagerdir = $(publicapidir)/accessibility-manager
-publicapialignmentdir = $(publicapicontrolsdir)/alignment
-publicapibuttonsdir = $(publicapicontrolsdir)/buttons
-publicapidefaultcontrolsdir = $(publicapicontrolsdir)/default-controls
-publicapigaussianblurviewdir = $(publicapicontrolsdir)/gaussian-blur-view
-publicapiimageviewdir = $(publicapicontrolsdir)/image-view
-publicapimodel3dviewdir = $(publicapicontrolsdir)/model3d-view
-publicapipageturnviewdir = $(publicapicontrolsdir)/page-turn-view
-publicapiscrollbardir = $(publicapicontrolsdir)/scroll-bar
-publicapiscrollabledir = $(publicapicontrolsdir)/scrollable
-publicapiscrollviewdir = $(publicapicontrolsdir)/scrollable/scroll-view
-publicapiitemviewdir = $(publicapicontrolsdir)/scrollable/item-view
-publicapitableviewdir = $(publicapicontrolsdir)/table-view
-publicapitextcontrolsdir = $(publicapicontrolsdir)/text-controls
-publicapifocusmanagerdir = $(publicapidir)/focus-manager
-publicapirenderingbackenddir = $(publicapidir)/text
+publicapidir = $(topleveldir)/public-api
+publicapicontrolsdir = $(publicapidir)/controls
+publicapiaccessibilitymanagerdir = $(publicapidir)/accessibility-manager
+publicapialignmentdir = $(publicapicontrolsdir)/alignment
+publicapibuttonsdir = $(publicapicontrolsdir)/buttons
+publicapidefaultcontrolsdir = $(publicapicontrolsdir)/default-controls
+publicapigaussianblurviewdir = $(publicapicontrolsdir)/gaussian-blur-view
+publicapiimageviewdir = $(publicapicontrolsdir)/image-view
+publicapimodel3dviewdir = $(publicapicontrolsdir)/model3d-view
+publicapipageturnviewdir = $(publicapicontrolsdir)/page-turn-view
+publicapiscrollbardir = $(publicapicontrolsdir)/scroll-bar
+publicapiscrollabledir = $(publicapicontrolsdir)/scrollable
+publicapiscrollviewdir = $(publicapicontrolsdir)/scrollable/scroll-view
+publicapiitemviewdir = $(publicapicontrolsdir)/scrollable/item-view
+publicapitableviewdir = $(publicapicontrolsdir)/table-view
+publicapitextcontrolsdir = $(publicapicontrolsdir)/text-controls
+publicapifocusmanagerdir = $(publicapidir)/focus-manager
+publicapirenderingbackenddir = $(publicapidir)/text
# public api headers
-publicapi_HEADERS = $(public_api_header_files)
-publicapicontrols_HEADERS = $(public_api_controls_header_files)
-develapiaccessibilitymanager_HEADERS = $(public_api_accessibility_manager_header_files)
-publicapialignment_HEADERS = $(public_api_alignment_header_files)
-publicapibuttons_HEADERS = $(public_api_buttons_header_files)
-publicapidefaultcontrols_HEADERS = $(public_api_default_controls_header_files)
-publicapigaussianblurview_HEADERS = $(public_api_gaussian_blur_view_header_files)
-publicapiimageview_HEADERS = $(public_api_image_view_header_files)
-publicapiitemview_HEADERS = $(public_api_item_view_header_files)
-publicapimodel3dview_HEADERS = $(public_api_model3d_view_header_files)
-publicapipageturnview_HEADERS = $(public_api_page_turn_view_header_files)
-publicapiscrollbar_HEADERS = $(public_api_scroll_bar_header_files)
-publicapiscrollable_HEADERS = $(public_api_scrollable_header_files)
-publicapiscrollview_HEADERS = $(public_api_scroll_view_header_files)
-publicapitableview_HEADERS = $(public_api_table_view_header_files)
-publicapitextcontrols_HEADERS = $(public_api_text_controls_header_files)
-publicapifocusmanager_HEADERS = $(public_api_focus_manager_header_files)
-publicapirenderingbackend_HEADERS = $(public_api_rendering_backend_header_files)
+publicapi_HEADERS = $(public_api_header_files)
+publicapicontrols_HEADERS = $(public_api_controls_header_files)
+publicapiaccessibilitymanager_HEADERS = $(public_api_accessibility_manager_header_files)
+publicapialignment_HEADERS = $(public_api_alignment_header_files)
+publicapibuttons_HEADERS = $(public_api_buttons_header_files)
+publicapidefaultcontrols_HEADERS = $(public_api_default_controls_header_files)
+publicapigaussianblurview_HEADERS = $(public_api_gaussian_blur_view_header_files)
+publicapiimageview_HEADERS = $(public_api_image_view_header_files)
+publicapiitemview_HEADERS = $(public_api_item_view_header_files)
+publicapimodel3dview_HEADERS = $(public_api_model3d_view_header_files)
+publicapipageturnview_HEADERS = $(public_api_page_turn_view_header_files)
+publicapiscrollbar_HEADERS = $(public_api_scroll_bar_header_files)
+publicapiscrollable_HEADERS = $(public_api_scrollable_header_files)
+publicapiscrollview_HEADERS = $(public_api_scroll_view_header_files)
+publicapitableview_HEADERS = $(public_api_table_view_header_files)
+publicapitextcontrols_HEADERS = $(public_api_text_controls_header_files)
+publicapifocusmanager_HEADERS = $(public_api_focus_manager_header_files)
+publicapirenderingbackend_HEADERS = $(public_api_rendering_backend_header_files)
# package doxygen file (contains doxygen grouping information)
packagedoxydir = $(topleveldir)/doc
# Shows all lines between public and private *inclusive*.
ALIASES += clip{3}="\dontinclude \1 \n \skip \2 \n \until \3"
+# <DALi Doxygen Tagging Rule>
+#
+# Use @SINCE_1_0, @SINCE_1_1, ... instead of @since,
+# and use @DEPRECATED_1_0, @DEPRECATED_1_1, ... instead of @deprecated.
+# It enables integrated management of version tagging between
+# the open source DALi API reference and Tizen API reference.
+# Using those tags with different ALIASES settings in each doxygen config file allows us
+# to generate two versions of "Since" and "Deprecated" generated output
+# from one set of public header files.
+#
+# If you need a newer version number like @SINCE_1_5 or @SINCE_2_0, just add new ALIASES for it.
+#
+# ##################################################3
+# # Guide for Open Source DALi API Reference
+#
+# ### @SINCE example:
+# [some-public-header.h]
+# /**
+# * ...
+# * @SINCE_1_0.1
+# */
+# void SomeFunction();
+#
+# [generated html file]
+# void SomeFunction()
+# ...
+# Since:
+# 1.0.1
+#
+# ### @DEPRECATED example 1:
+# [some-public-header.h]
+# /**
+# * @DEPRECATED_1_0.3
+# * ...
+# */
+# void SomeFunction();
+#
+# [generated html file]
+# void SomeFunction()
+# Deprecated:
+# Deprecated since 1.0.3
+# ...
+#
+# ### @DEPRECATED example 2:
+# [some-public-header.h]
+# ...
+# /**
+# * @DEPRECATED_1_0.3. Use SomeFunction2() instead.
+# * ...
+# */
+# void SomeFunction();
+#
+# [generated html file]
+# void SomeFunction()
+# Deprecated:
+# Deprecated since 1.0.3. Use SomeFunction2() instead.
+# ...
+#
+# ##################################################3
+# # Guide for Tizen Native API Reference
+#
+# ### @SINCE example:
+# [some-public-header.h]
+# /**
+# * ...
+# * @SINCE_1_0.1
+# */
+# void SomeFunction();
+#
+# [generated html file]
+# void SomeFunction()
+# ...
+# Since:
+# 2.4, DALi Version 1.0.1
+#
+# ### @DEPRECATED example 1:
+# [some-public-header.h]
+# /**
+# * @DEPRECATED_1_0.3
+# * ...
+# */
+# void SomeFunction();
+#
+# [generated html file]
+# void SomeFunction()
+# Deprecated:
+# Deprecated since 3.0, DALi version 1.0.3
+# ...
+#
+# ### @DEPRECATED example 2:
+# [some-public-header.h]
+# ...
+# /**
+# * @DEPRECATED_1_0.3. Use SomeFunction2() instead.
+# * ...
+# */
+# void SomeFunction();
+#
+# [generated html file]
+# void SomeFunction()
+# Deprecated:
+# Deprecated since 3.0, DALi version 1.0.3. Use SomeFunction2() instead.
+# ...
+
+###########################################
+# For Open Source DALi API Reference
+ALIASES += SINCE_1_0="@since 1.0"
+ALIASES += SINCE_1_1="@since 1.1"
+
+ALIASES += DEPRECATED_1_0="@deprecated Deprecated since 1.0"
+ALIASES += DEPRECATED_1_1="@deprecated Deprecated since 1.1"
+
+ALIASES += PLATFORM=""
+ALIASES += PRIVLEVEL_PLATFORM=""
+ALIASES += PRIVILEGE_KEYGRAB=""
+
+############################################
+## For Tizen Native API Reference
+#ALIASES += SINCE_1_0="\par Since:\n 2.4, DALi version 1.0"
+#ALIASES += SINCE_1_1="\par Since:\n 3.0, DALi version 1.1"
+
+## DALi has no deprecated API in Tizen 2.4 because it's DALi's first release.
+## Thus deprecated APIs in DALi 1.0.xx will be deprecated in Tizen 3.0.
+#ALIASES += DEPRECATED_1_0="@deprecated Deprecated since 3.0, DALi version 1.0"
+#ALIASES += DEPRECATED_1_1="@deprecated Deprecated since 3.0, DALi version 1.1"
+
+#ALIASES += PLATFORM="@platform"
+#ALIASES += PRIVLEVEL_PLATFORM="\par Privilege Level:\n platform"
+#ALIASES += PRIVILEGE_KEYGRAB="\par Privilege:\n http://tizen.org/privilege/keygrab"
+
+
# This tag can be used to specify a number of word-keyword mappings (TCL only).
# A mapping has the form "name=value". For example adding "class=itcl::class"
# will allow you to use the command class in the itcl::class meaning.
GetImpl(*this).SetBubbleDensity( density );
}
-void BubbleEmitter::SetBlendMode( bool enable )
-{
- GetImpl(*this).SetBlendMode( enable );
-}
-
void BubbleEmitter::EmitBubble( Animation& animation, const Vector2& emitPosition, const Vector2& direction, const Vector2& displacement )
{
GetImpl(*this).EmitBubble( animation, emitPosition, direction, displacement );
void SetBubbleDensity( unsigned int density );
/**
- * @brief Enable different blending mode for rendering.
- *
- * @param[in] enable If false, the default blending function if ImageActor is used.
- */
- void SetBlendMode( bool enable );
-
- /**
* @brief Add a bubble movement to the animation.
*
* @param[in] animation The animation reference.
ControlRenderer RendererFactory::GetControlRenderer( float borderSize, const Vector4& borderColor )
{
- return GetImplementation( *this ).GetControlRenderer( borderSize, borderColor );
+ return GetImplementation( *this ).GetControlRenderer( borderSize, borderColor, false );
+}
+
+
+ControlRenderer RendererFactory::GetControlRenderer( float borderSize, const Vector4& borderColor, bool antiAliasing )
+{
+ return GetImplementation( *this ).GetControlRenderer( borderSize, borderColor, antiAliasing );
}
ControlRenderer RendererFactory::GetControlRenderer( const Image& image )
ControlRenderer GetControlRenderer( float borderSize, const Vector4& borderColor );
/**
+ * @brief Request the control renderer to renderer the border with the given size and color, and specify whether anti-aliasing is needed.
+ *
+ * @param[in] borderSize The size of the border. Border size is the same along all edges.
+ * @param[in] borderColor The color of the border.
+ * @param[in] antiAliasing Whether anti-aliasing is required for border rendering.
+ * @return The pointer pointing to the control renderer
+ */
+ ControlRenderer GetControlRenderer( float borderSize, const Vector4& borderColor, bool antiAliasing );
+
+ /**
* @brief Request the control renderer to render the image.
*
* @param[in] image The image to be rendered.
--- /dev/null
+/*
+ * Copyright (c) 2016 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/controls/text-controls/text-editor.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/controls/text-controls/text-editor-impl.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+TextEditor TextEditor::New()
+{
+ return Internal::TextEditor::New();
+}
+
+TextEditor::TextEditor()
+{
+}
+
+TextEditor::TextEditor( const TextEditor& handle )
+: Control( handle )
+{
+}
+
+TextEditor& TextEditor::operator=( const TextEditor& handle )
+{
+ if( &handle != this )
+ {
+ Control::operator=( handle );
+ }
+ return *this;
+}
+
+TextEditor::~TextEditor()
+{
+}
+
+TextEditor TextEditor::DownCast( BaseHandle handle )
+{
+ return Control::DownCast<TextEditor, Internal::TextEditor>( handle );
+}
+
+TextEditor::TextChangedSignalType& TextEditor::TextChangedSignal()
+{
+ return Dali::Toolkit::GetImpl( *this ).TextChangedSignal();
+}
+
+TextEditor::TextEditor( Internal::TextEditor& implementation )
+: Control( implementation )
+{
+}
+
+TextEditor::TextEditor( Dali::Internal::CustomActor* internal )
+: Control( internal )
+{
+ VerifyCustomActorPointer<Internal::TextEditor>( internal );
+}
+
+} // namespace Toolkit
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_TOOLKIT_TEXT_EDITOR_H__
+#define __DALI_TOOLKIT_TEXT_EDITOR_H__
+
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/public-api/controls/control.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Internal DALI_INTERNAL
+{
+class TextEditor;
+}
+/**
+ * @addtogroup dali_toolkit_controls_text_controls
+ * @{
+ */
+
+/**
+ * @brief A control which provides a multi-line editable text editor.
+ *
+ * * Signals
+ * | %Signal Name | Method |
+ * |----------------------|-----------------------------------------------------|
+ * | textChanged | @ref TextChangedSignal() |
+ *
+ */
+class DALI_IMPORT_API TextEditor : public Control
+{
+public:
+
+ /**
+ * @brief The start and end property ranges for this control.
+ */
+ enum PropertyRange
+ {
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ };
+
+ /**
+ * @brief An enumeration of properties belonging to the TextEditor class.
+ */
+ struct Property
+ {
+ enum
+ {
+ RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "renderingBackend", The type or rendering e.g. bitmap-based, type INT
+ TEXT, ///< name "text", The text to display in UTF-8 format, type STRING
+ TEXT_COLOR, ///< name "textColor", The text color, type VECTOR4
+ FONT_FAMILY, ///< name "fontFamily", The requested font family, type STRING
+ FONT_STYLE, ///< name "fontStyle", The requested font style, type STRING
+ POINT_SIZE, ///< name "pointSize", The size of font in points, type FLOAT
+ HORIZONTAL_ALIGNMENT, ///< name "horizontalAlignment", The text horizontal alignment, type STRING, values "BEGIN", "CENTER", "END"
+ SCROLL_THRESHOLD, ///< name "scrollThreshold" Vertical scrolling will occur if the cursor is this close to the control border, type FLOAT
+ SCROLL_SPEED, ///< name "scrollSpeed" The scroll speed in pixels per second, type FLOAT
+ PRIMARY_CURSOR_COLOR, ///< name "primaryCursorColor", The color to apply to the primary cursor, type VECTOR4
+ SECONDARY_CURSOR_COLOR, ///< name "secondaryCursorColor", The color to apply to the secondary cursor, type VECTOR4
+ ENABLE_CURSOR_BLINK, ///< name "enableCursorBlink", Whether the cursor should blink or not, type BOOLEAN
+ CURSOR_BLINK_INTERVAL, ///< name "cursorBlinkInterval", The time interval in seconds between cursor on/off states, type FLOAT
+ CURSOR_BLINK_DURATION, ///< name "cursorBlinkDuration", The cursor will stop blinking after this number of seconds (if non-zero), type FLOAT
+ CURSOR_WIDTH, ///< name "cursorWidth", The cursor width, type INTEGER
+ GRAB_HANDLE_IMAGE, ///< name "grabHandleImage", The image to display for the grab handle, type STRING
+ GRAB_HANDLE_PRESSED_IMAGE, ///< name "grabHandlePressedImage", The image to display when the grab handle is pressed, type STRING
+ SELECTION_HANDLE_IMAGE_LEFT, ///< name "selectionHandleImageLeft", The image to display for the left selection handle, type MAP
+ SELECTION_HANDLE_IMAGE_RIGHT, ///< name "selectionHandleImageRight", The image to display for the right selection handle, type MAP
+ SELECTION_HANDLE_PRESSED_IMAGE_LEFT, ///< name "selectionHandlePressedImageLeft", The image to display when the left selection handle is pressed, type MAP
+ SELECTION_HANDLE_PRESSED_IMAGE_RIGHT, ///< name "selectionHandlePressedImageRight", The image to display when the right selection handle is pressed, type MAP
+ SELECTION_HANDLE_MARKER_IMAGE_LEFT, ///< name "selectionHandleMarkerImageLeft", The image to display for the left selection handle marker, type MAP
+ SELECTION_HANDLE_MARKER_IMAGE_RIGHT, ///< name "selectionHandleMarkerImageRight", The image to display for the right selection handle marker, type MAP
+ SELECTION_HIGHLIGHT_COLOR, ///< name "selectionHighlightColor", The color of the selection highlight, type VECTOR4
+ DECORATION_BOUNDING_BOX, ///< name "decorationBoundingBox", The decorations (handles etc) will positioned within this area on-screen, type RECTANGLE
+ ENABLE_MARKUP, ///< name "enableMarkup", Whether the mark-up processing is enabled. type BOOLEAN
+ INPUT_COLOR, ///< name "inputColor", The color of the new input text, type VECTOR4
+ INPUT_FONT_FAMILY, ///< name "inputFontFamily", The font's family of the new input text, type STRING
+ INPUT_FONT_STYLE, ///< name "inputFontStyle", The font's style of the new input text, type STRING
+ INPUT_POINT_SIZE ///< name "inputPointSize", The font's size of the new input text in points, type FLOAT
+ };
+ };
+
+ // Type Defs
+
+ /// @brief Text changed signal type.
+ typedef Signal<void ( TextEditor ) > TextChangedSignalType;
+
+ /**
+ * @brief Create the TextEditor control.
+ * @return A handle to the TextEditor control.
+ */
+ static TextEditor New();
+
+ /**
+ * @brief Creates an empty handle.
+ */
+ TextEditor();
+
+ /**
+ * @brief Copy constructor.
+ *
+ * @param[in] handle The handle to copy from.
+ */
+ TextEditor( const TextEditor& handle );
+
+ /**
+ * @brief Assignment operator.
+ *
+ * @param[in] handle The handle to copy from.
+ * @return A reference to this.
+ */
+ TextEditor& operator=( const TextEditor& handle );
+
+ /**
+ * @brief Destructor.
+ *
+ * This is non-virtual since derived Handle types must not contain data or virtual methods.
+ */
+ ~TextEditor();
+
+ /**
+ * @brief Downcast a handle to TextEditor.
+ *
+ * If the BaseHandle points is a TextEditor the downcast returns a valid handle.
+ * If not the returned handle is left empty.
+ *
+ * @param[in] handle Handle to an object.
+ * @return handle to a TextEditor or an empty handle.
+ */
+ static TextEditor DownCast( BaseHandle handle );
+
+ // Signals
+
+ /**
+ * @brief This signal is emitted when the text changes.
+ *
+ * A callback of the following type may be connected:
+ * @code
+ * void YourCallbackName( TextEditor textEditor );
+ * @endcode
+ * @return The signal to connect to.
+ */
+ TextChangedSignalType& TextChangedSignal();
+
+public: // Not intended for application developers
+
+ /**
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ *
+ * @param[in] implementation The Control implementation.
+ */
+ DALI_INTERNAL TextEditor( Internal::TextEditor& implementation );
+
+ /**
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ *
+ * @param[in] internal A pointer to the internal CustomActor.
+ */
+ explicit DALI_INTERNAL TextEditor( Dali::Internal::CustomActor* internal );
+};
+
+/**
+ * @}
+ */
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_TEXT_EDITOR_H__
$(devel_api_src_dir)/controls/shadow-view/shadow-view.cpp \
$(devel_api_src_dir)/controls/slider/slider.cpp \
$(devel_api_src_dir)/controls/super-blur-view/super-blur-view.cpp \
+ $(devel_api_src_dir)/controls/text-controls/text-editor.cpp \
$(devel_api_src_dir)/controls/text-controls/text-selection-popup.cpp \
$(devel_api_src_dir)/controls/text-controls/text-selection-toolbar.cpp \
$(devel_api_src_dir)/controls/tool-bar/tool-bar.cpp \
# Add devel header files here
+devel_api_controls_header_files = \
+ $(devel_api_src_dir)/controls/control-depth-index-ranges.h
+
devel_api_bloom_view_header_files = \
$(devel_api_src_dir)/controls/bloom-view/bloom-view.h
$(devel_api_src_dir)/controls/super-blur-view/super-blur-view.h
devel_api_text_controls_header_files = \
+ $(devel_api_src_dir)/controls/text-controls/text-editor.h \
$(devel_api_src_dir)/controls/text-controls/text-selection-popup.h \
$(devel_api_src_dir)/controls/text-controls/text-selection-toolbar.h
"void main()\n"
"{\n"
" mediump float lighting = 0.25;\n"
- " mediump vec4 position = uModelView * vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ " mediump vec4 position = uModelView * vec4(aPosition, 1.0);\n"
"\n"
" mediump vec2 d = position.xy - uCenter;\n"
" mediump float dist = max( 0.0, dot(d,uDirection) );\n"
"\n"
"vShade = 1.0 - abs(sn) * lighting;\n"
"\n"
- "vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ "vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
"}" );
std::string fragmentShader(
"\n"
"void main()\n"
"{\n"
- " mediump vec4 world = uModelView * vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ " mediump vec4 world = uModelView * vec4(aPosition, 1.0);\n"
" mediump vec2 d = (world.xy - uCenter) * uAnglePerUnit;\n"
" mediump float a = length(d);\n"
" mediump float cs = cos(radians(a));\n"
" world.z -= cs * uRadius;\n"
" gl_Position = uProjection * world;\n"
" \n"
- " vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ " vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
"}\n");
ShaderEffect shaderEffect = ShaderEffect::New(
"varying float vPercentage;\n"
"void main()\n"
"{\n"
- " vec4 position = uModelView * vec4( aPosition*uSize.xy, 0.0, 1.0 );\n"
+ " vec4 position = uModelView * vec4( aPosition, 1.0 );\n"
" float percentage = 0.0;\n"
" for( int i=0; i<NUMBER_OF_DIMPLE; ++i )\n"
" {\n"
" }\n"
" vPercentage = clamp( percentage, 0.0, 1.0 );\n"
" gl_Position = uProjection * position;\n"
- " vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ " vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
"}\n");
vertexShaderStringStream << vertexShader;
"\n"
"void main()\n"
"{\n"
- " mediump vec4 world = uModelView * vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ " mediump vec4 world = uModelView * vec4(aPosition, 1.0);\n"
" gl_Position = uProjection * world;\n"
" \n"
- " vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );;\n"
+ " vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
" vRelativePosition = vTexCoord - uCenter;\n"
"}\n");
std::string vertexShader(
"void main() \n"
"{ \n"
- " mediump vec3 pos = vec3(aPosition, 0.0)*uSize; \n"
+ " mediump vec3 pos = aPosition; \n"
" pos.y = pos.y * 3.0; \n"
" mediump vec4 world = uModelView * vec4(pos,1.0); \n"
" gl_Position = uProjection * world; \n"
- " vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) ); \n"
+ " vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord ); \n"
"} \n" );
std::string fragmentShader(
"{\n"
"float lighting = uAmplitude * 0.02;\n"
"float waveLength = uAmplitude * 0.0016;\n"
- "vec4 world = uModelView * vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ "vec4 world = uModelView * vec4(aPosition, 1.0);\n"
"vec2 d = vec2(world.x - uCenter.x, world.y - uCenter.y);\n"
"float dist = length(d);\n"
"float amplitude = cos(uTime - dist*waveLength);\n"
"}\n"
"vShade = 1.0 - (dot * slope);\n"
"vLight = max(0.0, dot * -slope);\n"
- "vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ "vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
"}" );
// append the default version
"uniform float uTime;\n"
"void main()\n"
"{\n"
- " highp vec2 textureSize = uTextureRect.zw - uTextureRect.xy;\n"
+ " highp vec2 textureSize = sTextureRect.zw - sTextureRect.xy;\n"
" highp vec2 pos = -1.0 + 2.0 * vTexCoord.st/textureSize;\n"
" highp float len = length(pos);\n"
" highp vec2 texCoord = vTexCoord.st/textureSize + pos/len * sin( len * 12.0 - uTime * 4.0 ) * uAmplitude;\n"
"\n"
"void main()\n"
"{\n"
- "mediump vec4 world = uModelView * vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ "mediump vec4 world = uModelView * vec4(aPosition, 1.0);\n"
"\n"
"world.x = world.x + tan(radians(uAngleXAxis)) * (world.y - uCenter.y * world.w);\n"
"world.y = world.y + tan(radians(uAngleYAxis)) * (world.x - uCenter.x * world.w);\n"
"\n"
"gl_Position = uProjection * world;\n"
"\n"
- "vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ "vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
"}" );
// Create the implementation, temporarily owned on stack,
"void main()\n"
"{\n"
- " vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ " vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
// Get the rect coords of the effect region in -1..1 range, i.e. circle centred around the center of the rect
// Done in the vertex shader itself to make use of gl interpolation for varying.
" vCentredCoord = vec2( ( (vTexCoord.x - uEffectRegion.x)/(uEffectRegion.z - uEffectRegion.x) * 2.0 - 1.0 ), ( (vTexCoord.y - uEffectRegion.y)/(uEffectRegion.w - uEffectRegion.y) * 2.0 - 1.0 ) );\n"
- " gl_Position = uMvpMatrix * vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ " gl_Position = uMvpMatrix * vec4(aPosition, 1.0);\n"
"}\n";
std::string fragmentSourceFixed;
"\n"
"void main()\n"
"{\n"
- " mediump vec4 world = vec4(aPosition*uSize.xy, 0.0, 1.0);\n"
+ " mediump vec4 world = vec4(aPosition, 1.0);\n"
" \n"
" mediump vec2 d = vec2(world.xy - uCenter);\n"
" mediump float dist = length(d);\n"
" vRange = max(0.1, range);\n"
" \n"
" gl_Position = uMvpMatrix * world;\n"
- " vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;\n"
+ " vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n"
"}");
std::string fragmentShader(
"uniform mediump vec2 uCenter;\n"
"void main()\n"
"{\n"
- " highp vec2 textureCenter = (uTextureRect.xy + uTextureRect.zw) * 0.5;\n"
+ " highp vec2 textureCenter = (sTextureRect.xy + sTextureRect.zw) * 0.5;\n"
" textureCenter = vTexCoord.st - textureCenter;\n"
" highp float distance = length(textureCenter);\n"
" if (distance >= uRadius)\n"
/*
- * Copyright (c) 2014 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2016 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.
{
using namespace Dali::Scripting;
-extern bool SetPropertyFromNode( const TreeNode& node, Property::Value& value, const Replacement& constant );
+extern void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value, const Replacement& constant );
/*
* Handles special case actor configuration (anything thats not already a property)
std::string key( keyChild.first );
Property::Value value;
- if( SetPropertyFromNode( keyChild.second, value, constant ))
- {
- // Register/Set property.
- actor.RegisterProperty( key, value, Property::READ_WRITE );
- }
+ DeterminePropertyFromNode( keyChild.second, value, constant );
+ // Register/Set property.
+ actor.RegisterProperty( key, value, Property::READ_WRITE );
}
}
/*
- * Copyright (c) 2014 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2016 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.
class Replacement;
extern Animation CreateAnimation(const TreeNode& child, const Replacement& replacements, const Dali::Actor searchRoot, Builder* const builder );
-extern bool SetPropertyFromNode( const TreeNode& node, Property::Value& value );
-extern bool SetPropertyFromNode( const TreeNode& node, Property::Value& value, const Replacement& replacements );
-extern bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value );
-extern bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value, const Replacement& replacements );
+extern void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value );
+extern void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value, const Replacement& replacements );
+extern bool DeterminePropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value );
+extern bool DeterminePropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value, const Replacement& replacements );
extern Actor SetupSignalAction(ConnectionTracker* tracker, const TreeNode &root, const TreeNode &child, Actor actor, Dali::Toolkit::Internal::Builder* const builder);
extern Actor SetupPropertyNotification(ConnectionTracker* tracker, const TreeNode &root, const TreeNode &child, Actor actor, Dali::Toolkit::Internal::Builder* const builder);
extern Actor SetupActor( const TreeNode& node, Actor& actor, const Replacement& constant );
Property::Type type = propertyObject.GetPropertyType(index);
Property::Value value;
- if( !SetPropertyFromNode( keyChild.second, type, value, constant ) )
+ if( !DeterminePropertyFromNode( keyChild.second, type, value, constant ) )
{
// verbose as this might not be a problem
// eg parentOrigin can be a string which is picked up later
if( OptionalChild effect = IsChild( *effects, name ) )
{
Dali::Property::Value propertyMap(Property::MAP);
- if( SetPropertyFromNode( *effect, Property::MAP, propertyMap, constant ) )
+ if( DeterminePropertyFromNode( *effect, Property::MAP, propertyMap, constant ) )
{
ret = Dali::Scripting::NewShaderEffect( propertyMap );
mShaderEffectLut[ name ] = ret;
if( OptionalChild image = IsChild( *images, name ) )
{
Dali::Property::Value property(Property::MAP);
- if( SetPropertyFromNode( *image, Property::MAP, property, constant ) )
+ if( DeterminePropertyFromNode( *image, Property::MAP, property, constant ) )
{
Property::Map* map = property.GetMap();
if( OptionalChild pointsProperty = IsChild( *path, "points") )
{
Dali::Property::Value points(Property::ARRAY);
- if( SetPropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
+ if( DeterminePropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
{
ret = Path::New();
ret.SetProperty( Path::Property::POINTS, points);
if( OptionalChild pointsProperty = IsChild( *path, "controlPoints") )
{
Dali::Property::Value points(Property::ARRAY);
- if( SetPropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
+ if( DeterminePropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
{
ret.SetProperty( Path::Property::CONTROL_POINTS, points);
}
if( OptionalChild pointsProperty = IsChild( *pathConstrainer, "points") )
{
Dali::Property::Value points(Property::ARRAY);
- if( SetPropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
+ if( DeterminePropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
{
ret = PathConstrainer::New();
ret.SetProperty( PathConstrainer::Property::POINTS, points);
if( OptionalChild pointsProperty = IsChild( *pathConstrainer, "controlPoints") )
{
Dali::Property::Value points(Property::ARRAY);
- if( SetPropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
+ if( DeterminePropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
{
ret.SetProperty( PathConstrainer::Property::CONTROL_POINTS, points);
}
if( OptionalChild pointsProperty = IsChild( *linearConstrainer, "value") )
{
Dali::Property::Value points(Property::ARRAY);
- if( SetPropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
+ if( DeterminePropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
{
ret = Dali::LinearConstrainer::New();
ret.SetProperty( LinearConstrainer::Property::VALUE, points);
if( OptionalChild pointsProperty = IsChild( *linearConstrainer, "progress") )
{
Dali::Property::Value points(Property::ARRAY);
- if( SetPropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
+ if( DeterminePropertyFromNode( *pointsProperty, Property::ARRAY, points ) )
{
ret.SetProperty( LinearConstrainer::Property::PROGRESS, points);
}
parser.GetErrorDescription().c_str() );
DALI_ASSERT_ALWAYS(!"Cannot parse JSON");
-
}
else
{
}
DALI_ASSERT_ALWAYS(mParser.GetRoot() && "Cannot parse JSON");
-
}
void Builder::AddConstants( const Property::Map& map )
#if defined(DEBUG_ENABLED)
DALI_SCRIPT_VERBOSE("Constant set from json '%s'\n", (*iter).second.GetName());
#endif
- if( SetPropertyFromNode( (*iter).second, property, replacer ) )
- {
- intoMap[ (*iter).second.GetName() ] = property;
- }
- else
- {
- DALI_SCRIPT_WARNING("Cannot convert property for constant %s\n",
- (*iter).second.GetName() == NULL ? "no name?" : (*iter).second.GetName());
- }
+ DeterminePropertyFromNode( (*iter).second, property, replacer );
+ intoMap[ (*iter).second.GetName() ] = property;
}
}
}
mParser = Dali::Toolkit::JsonParser::New();
Property::Map defaultDirs;
- defaultDirs[ TOKEN_STRING(DALI_IMAGE_DIR) ] = DALI_IMAGE_DIR;
- defaultDirs[ TOKEN_STRING(DALI_SOUND_DIR) ] = DALI_SOUND_DIR;
- defaultDirs[ TOKEN_STRING(DALI_STYLE_DIR) ] = DALI_STYLE_DIR;
+ defaultDirs[ TOKEN_STRING(DALI_IMAGE_DIR) ] = DALI_IMAGE_DIR;
+ defaultDirs[ TOKEN_STRING(DALI_SOUND_DIR) ] = DALI_SOUND_DIR;
+ defaultDirs[ TOKEN_STRING(DALI_STYLE_DIR) ] = DALI_STYLE_DIR;
defaultDirs[ TOKEN_STRING(DALI_STYLE_IMAGE_DIR) ] = DALI_STYLE_IMAGE_DIR;
AddConstants( defaultDirs );
/*
- * Copyright (c) 2015 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2016 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.
/*
* Set a property value from a tree node.
- * This function guesses the type of the property from the format of the string in the node.
- * This is not always possible and could be surprising.
+ * This function determines the type of the property from the format of the string in the node.
+ * This is not always possible and if the type cannot be determined then then the type will default to Array.
* @param node The node string to convert from
* @param value The property value to set
- * @return true if the string could be converted.
*/
-bool SetPropertyFromNode( const TreeNode& node, Property::Value& value );
+void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value );
/*
* Set a property value from a tree node as SetPropertyFromNode() above
+ * This function determines the type of the property from the format of the string in the node.
+ * This is not always possible and if the type cannot be determined then then the type will default to Array.
* @param node The node string to convert from
* @param value The property value to set
* @param replacement The overriding replacement map (if any)
- * @return true if the string could be converted.
*/
-bool SetPropertyFromNode( const TreeNode& node, Property::Value& value,
+void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value,
const Replacement& replacement );
/*
* @param value The property value to set
* @return true if the string could be converted to the correct type.
*/
-bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value );
+bool DeterminePropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value );
/*
* Set a property value as the given type from a tree node as SetPropertyFromNode() above
* @param replacement The overriding replacement map (if any)
* @return true if the string could be converted to the correct type.
*/
-bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value,
+bool DeterminePropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value,
const Replacement& replacement );
// type-cast and value keys. If they do then a work around is to add a bogus key to not run this case.
if(*childType == "boolean")
{
- return SetPropertyFromNode( *childValue, Dali::Property::BOOLEAN, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::BOOLEAN, value, replacement);
}
else if(*childType == "float")
{
- return SetPropertyFromNode( *childValue, Dali::Property::FLOAT, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::FLOAT, value, replacement);
}
else if(*childType == "vector2")
{
- return SetPropertyFromNode( *childValue, Dali::Property::VECTOR2, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::VECTOR2, value, replacement);
}
else if(*childType == "vector3")
{
- return SetPropertyFromNode( *childValue, Dali::Property::VECTOR3, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::VECTOR3, value, replacement);
}
else if(*childType == "vector4")
{
- return SetPropertyFromNode( *childValue, Dali::Property::VECTOR4, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::VECTOR4, value, replacement);
}
else if(*childType == "rotation")
{
- return SetPropertyFromNode( *childValue, Dali::Property::ROTATION, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::ROTATION, value, replacement);
}
else if(*childType == "rect")
{
- return SetPropertyFromNode( *childValue, Dali::Property::RECTANGLE, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::RECTANGLE, value, replacement);
}
else if(*childType == "string")
{
- return SetPropertyFromNode( *childValue, Dali::Property::STRING, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::STRING, value, replacement);
}
else if(*childType == "map")
{
- return SetPropertyFromNode( *childValue, Dali::Property::MAP, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::MAP, value, replacement);
}
else if(*childType == "array")
{
- return SetPropertyFromNode( *childValue, Dali::Property::ARRAY, value, replacement);
+ return DeterminePropertyFromNode( *childValue, Dali::Property::ARRAY, value, replacement);
}
}
}
-bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value)
+bool DeterminePropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value)
{
Replacement noReplacement;
- return SetPropertyFromNode( node, type, value, noReplacement );
+ return DeterminePropertyFromNode( node, type, value, noReplacement );
}
-bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value,
+bool DeterminePropertyFromNode( const TreeNode& node, Property::Type type, Property::Value& value,
const Replacement& replacer )
{
bool done = false;
for( ; i < node.Size(); ++i, ++iter)
{
Property::Value childValue;
- if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
- {
- array->PushBack( childValue );
- }
+ DeterminePropertyFromNode( (*iter).second, childValue, replacer );
+ array->PushBack( childValue );
}
- if( array->Count() == node.Size() )
- {
- done = true;
- }
- else
- {
- done = false;
- }
+ done = ( array->Count() == node.Size() );
}
}
break;
for( ; i < node.Size(); ++i, ++iter)
{
Property::Value childValue;
- if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
- {
- map->Insert( (*iter).first, childValue );
- }
+ DeterminePropertyFromNode( (*iter).second, childValue, replacer );
+ map->Insert( (*iter).first, childValue );
}
- if( map->Count() == node.Size() )
- {
- done = true;
- }
- else
- {
- done = false;
- }
+ done = ( map->Count() == node.Size() );
}
}
break;
return done;
}
-bool SetPropertyFromNode( const TreeNode& node, Property::Value& value )
+void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value )
{
Replacement replacer;
- return SetPropertyFromNode( node, value, replacer );
+ DeterminePropertyFromNode( node, value, replacer );
}
-bool SetPropertyFromNode( const TreeNode& node, Property::Value& value,
+void DeterminePropertyFromNode( const TreeNode& node, Property::Value& value,
const Replacement& replacer )
{
- bool done = false;
- // some values are ambiguous as we have no Property::Type but can be disambiguated in the json
+ TreeNode::NodeType nodeType = node.GetType();
- // Currently Rotations and Rectangle must always be disambiguated when a type isnt available
- if( Disambiguated( node, value, replacer ) )
- {
- done = true;
- }
- else
+ // Some values are ambiguous as we have no Property::Type but can be disambiguated in the JSON.
+ // Currently Rotations and Rectangle must always be disambiguated when a type isn't available
+ if( !Disambiguated( node, value, replacer ) )
{
+ bool done = false;
+
+ // Here, nodes are handled with the following precedence order:
+ // 1) Nodes with children, that have type ARRAY: Checked for array types including vectors and matrices.
+ // 2) Nodes without children, that do not have type ARRAY OR OBJECT: Checked for primitive types (int / float /etc).
+ // 3) If no match so far; If type is OBJECT: attempt to create as a Property::Map.
+ // 4) If no match still; Create as array.
+
+ // First handle nodes with children.
if( node.Size() )
{
- // our current heuristic for deciding an array is actually a vector and not say a map
- // is to check if the values are all floats
- bool allNumbers = true;
- for(TreeConstIter iter = node.CBegin(); iter != node.CEnd(); ++iter)
+ // Handle array types.
+ if( nodeType == TreeNode::ARRAY )
{
- OptionalFloat f = IsFloat((*iter).second);
- if(!f)
+ // our current heuristic for deciding an array is actually a vector and not say a map
+ // is to check if the values are all floats
+ bool allNumbers = true;
+ for( TreeConstIter iter = node.CBegin(); iter != node.CEnd(); ++iter )
{
- allNumbers = false;
- break;
+ OptionalFloat checkFloat = IsFloat( ( *iter ).second );
+ if( !checkFloat )
+ {
+ allNumbers = false;
+ break;
+ }
}
- }
- if( allNumbers )
- {
- // prefer finding vectors over presuming composite Property::Array...
- if( OptionalMatrix v = IsMatrix(node) )
- {
- value = *v;
- done = true;
- }
- else if( OptionalMatrix3 v = IsMatrix3(node) )
- {
- value = *v;
- done = true;
- }
- else if( OptionalVector4 v = IsVector4(node) )
- {
- value = *v;
- done = true;
- }
- else if( OptionalVector3 v = IsVector3(node) )
- {
- value = *v;
- done = true;
- }
- else if( OptionalVector2 v = IsVector2(node) )
- {
- value = *v;
- done = true;
- }
- else if( 4 == node.Size() )
+ if( allNumbers )
{
- if( OptionalVector4 v = IsVector4(node) )
+ // prefer finding vectors over presuming composite Property::Array...
+ if( OptionalMatrix v = IsMatrix( node ) )
{
value = *v;
done = true;
}
- }
- else
- {
- value = Property::Value(Property::ARRAY);
- Property::Array* array = value.GetArray();
-
- if( array )
+ else if( OptionalMatrix3 v = IsMatrix3( node ) )
{
- for(TreeConstIter iter = node.CBegin(); iter != node.CEnd(); ++iter)
- {
- Property::Value childValue;
- if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
- {
- array->PushBack( childValue );
- done = true;
- }
- }
+ value = *v;
+ done = true;
}
- }
- }
-
- if(!done)
- {
- // presume an array or map
- // container of size 1
- TreeNode::ConstIterator iter = node.CBegin();
-
- // its seems legal with current json parser for a map to have an empty key
- // but here we take that to mean the structure is a list
- if( ((*iter).first) == 0 )
- {
- value = Property::Value(Property::ARRAY);
- Property::Array* array = value.GetArray();
-
- if( array )
+ else if( OptionalVector4 v = IsVector4( node ) )
{
- for(unsigned int i = 0; i < node.Size(); ++i, ++iter)
- {
- Property::Value childValue;
- if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
- {
- array->PushBack( childValue );
- done = true;
- }
- }
+ value = *v;
+ done = true;
}
- }
- else
- {
- value = Property::Value(Property::MAP);
- Property::Map* map = value.GetMap();
-
- if( map )
+ else if( OptionalVector3 v = IsVector3( node ) )
{
- for(unsigned int i = 0; i < node.Size(); ++i, ++iter)
+ value = *v;
+ done = true;
+ }
+ else if( OptionalVector2 v = IsVector2( node ) )
+ {
+ value = *v;
+ done = true;
+ }
+ else if( 4 == node.Size() )
+ {
+ if( OptionalVector4 v = IsVector4( node ) )
{
- Property::Value childValue;
- if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
- {
- map->Insert( (*iter).first, childValue );
- done = true;
- }
+ value = *v;
+ done = true;
}
}
}
- } // if!done
+ }
} // if node.size()
- else // if( 0 == node.size() )
+ else if( ( nodeType != TreeNode::OBJECT ) && ( nodeType != TreeNode::ARRAY ) )
{
// no children so either one of bool, float, integer, string
- OptionalBoolean aBool = replacer.IsBoolean(node);
- OptionalInteger anInt = replacer.IsInteger(node);
- OptionalFloat aFloat = replacer.IsFloat(node);
- OptionalString aString = replacer.IsString(node);
+ OptionalBoolean aBool = replacer.IsBoolean( node );
+ OptionalInteger anInt = replacer.IsInteger( node );
+ OptionalFloat aFloat = replacer.IsFloat( node );
+ OptionalString aString = replacer.IsString( node );
- if(aBool)
+ if( aBool )
{
// a bool is also an int but here we presume int
- if(anInt)
+ if( anInt )
{
value = *anInt;
- done = true;
}
else
{
value = *aBool;
- done = true;
}
}
else
// {"value":"123"}
// {"value":123}
// This means we can't have a string with purely numeric content without disambiguation.
- if(aFloat)
+ if( aFloat )
{
value = *aFloat;
- done = true;
}
- else if(anInt)
+ else if( anInt )
{
value = *anInt;
- done = true;
}
else
{
// string always succeeds with the current json parser so its last
value = *aString;
- done = true;
}
-
} // if aBool
+ done = true;
} // if( node.size() )
- } // if Disambiguated()
+ // If we have not created a value so far, attempt to create a Map or Array.
+ if( !done )
+ {
+ // We are guaranteed to have at least one entry as this has been checked already.
+ TreeConstIter containerIterator = node.CBegin();
+ TreeConstIter containerEnd = node.CEnd();
- return done;
-} // bool SetPropertyFromNode( const TreeNode& node, Property::Value& value )
+ // The TreeNode::OBJECT type implies a Property::Map.
+ if( nodeType == TreeNode::OBJECT )
+ {
+ // We have a key, treat container as a Map.
+ value = Property::Value( Property::MAP );
+ Property::Map* map = value.GetMap();
+
+ if( map )
+ {
+ // Iterate through container to add all entries.
+ for( ; containerIterator != containerEnd; ++containerIterator )
+ {
+ Property::Value childValue;
+ DeterminePropertyFromNode( ( *containerIterator ).second, childValue, replacer );
+ map->Insert( ( *containerIterator ).first, childValue );
+ }
+ }
+ }
+ else
+ {
+ // We don't have a key, treat container as an array.
+ // Note: We don't check if the node type is array here, as we want to cope with unknowns by creating an array also.
+ // This is the fall-back if no other types could be created.
+ value = Property::Value( Property::ARRAY );
+ Property::Array* array = value.GetArray();
+
+ if( array )
+ {
+ // Iterate through container to add all entries.
+ for( ; containerIterator != containerEnd; ++containerIterator )
+ {
+ Property::Value childValue;
+ DeterminePropertyFromNode( ( *containerIterator ).second, childValue, replacer );
+ array->PushBack( childValue );
+ }
+ }
+ }
+ } // if !done
+ } // if !Disambiguated()
+}
} // namespace Internal
/*
- * Copyright (c) 2014 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2016 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.
namespace Internal
{
extern Animation CreateAnimation( const TreeNode& child, Dali::Toolkit::Internal::Builder* const builder );
-extern bool SetPropertyFromNode( const TreeNode& node, Property::Value& value );
+extern bool DeterminePropertyFromNode( const TreeNode& node, Property::Value& value );
}
}
}
if(0 == nChildren)
{
// cast away unused return for static analyzers
- static_cast<void>( Dali::Toolkit::Internal::SetPropertyFromNode( child, ret ) );
+ static_cast<void>( Dali::Toolkit::Internal::DeterminePropertyFromNode( child, ret ) );
}
else if(1 == nChildren)
{
action.actorName = *actorName;
action.propertyName = *propertyName;
// actor may not exist yet so we can't check the property type
- if( !Dali::Toolkit::Internal::SetPropertyFromNode( *valueChild, action.value ) )
- {
- DALI_SCRIPT_WARNING("Cannot set property for set property action\n");
- }
+ Dali::Toolkit::Internal::DeterminePropertyFromNode( *valueChild, action.value );
connector.Connect( action );
}
else
TreeNodeManipulator modify(node);
modify.SetName(name);
- // Set the type of the existing node, this may remove children where necessary
- // (changing from container type to value type)
+
+ // Set the type of the existing node.
+ // Where the new type is different, then any children of this node will
+ // be deleted.
+ // When the type is an array of numbers, then this will also remove any children
+ // When the type is an object or other array, then the children will not be removed,
+ // but will instead follow these replace rules.
modify.SetType(type);
mCurrent = modify;
namespace
{
-void Indent(std::ostream& o, int indent)
+void Indent(std::ostream& o, int level, int indentWidth)
{
- for (int i = 0; i < indent; ++i)
+ for (int i = 0; i < level*indentWidth; ++i)
{
o << " ";
}
}
+std::string EscapeQuotes( const char* aString)
+{
+ std::string escapedString;
+ int length = strlen(aString);
+ escapedString.reserve(length);
+
+ const char* end = aString+length;
+ for( const char* iter = aString; iter != end ; ++iter)
+ {
+ if(*iter != '\"')
+ {
+ escapedString.push_back(*iter);
+ }
+ else
+ {
+ escapedString.append("\\\"");
+ }
+ }
+ return escapedString;
}
+} // anonymous namespace
+
TreeNodeManipulator::TreeNodeManipulator(TreeNode* node)
: mNode(node)
{
}
}
}
+ else if( TreeNode::ARRAY == mNode->mType )
+ {
+ if( mNode->mFirstChild != NULL )
+ {
+ TreeNode::NodeType type = mNode->mFirstChild->GetType();
+
+ if( TreeNode::FLOAT == type || TreeNode::INTEGER == type )
+ {
+ // Arrays of numbers should be replaced, not appended to.
+ RemoveChildren();
+ }
+ }
+ }
}
void TreeNodeManipulator::SetName( const char* name )
void TreeNodeManipulator::Write(std::ostream& output, int indent) const
{
DALI_ASSERT_DEBUG(mNode && "Operation on NULL JSON node");
- DoWrite(mNode, output, indent);
+ DoWrite(mNode, output, 0, indent, false);
}
-void TreeNodeManipulator::DoWrite(const TreeNode *value, std::ostream& output, int indent) const
+void TreeNodeManipulator::DoWrite(const TreeNode *value, std::ostream& output, int level, int indentWidth, bool groupChildren) const
{
DALI_ASSERT_DEBUG(value && "Operation on NULL JSON node");
- Indent(output, indent);
+ if(!groupChildren)
+ {
+ Indent(output, level, indentWidth);
+ }
if (value->GetName())
{
output << "null";
if(NULL != value->mNextSibling)
{
- output << ",";
+ output << ", ";
}
- if(indent)
+ if( !groupChildren )
{
output << std::endl;
}
case TreeNode::OBJECT:
case TreeNode::ARRAY:
{
+ bool groupMyChildren = false;
+
+ if( TreeNode::ARRAY == value->GetType() &&
+ ( TreeNode::INTEGER == value->mFirstChild->GetType() ||
+ TreeNode::FLOAT == value->mFirstChild->GetType() ) )
+ {
+ groupMyChildren = true;
+ }
+
if( value->GetType() == TreeNode::OBJECT)
{
+ output << std::endl;
+ Indent(output, level, indentWidth);
output << "{";
- if(indent)
- {
- output << std::endl;
- }
}
else
{
- output << "[";
- if(indent)
+ if( !groupMyChildren )
{
output << std::endl;
+ Indent(output, level, indentWidth);
}
+ output << "[";
+ }
+
+ if( groupMyChildren )
+ {
+ output << " ";
+ }
+ else
+ {
+ output << std::endl;
}
for (TreeNode::ConstIterator it = value->CBegin(); it != value->CEnd(); ++it)
{
- DoWrite( &((*it).second), output, indent + 1);
+ DoWrite( &((*it).second), output, level+1, indentWidth, groupMyChildren );
}
- Indent(output, indent);
+
+ if( !groupMyChildren )
+ {
+ Indent(output, level, indentWidth);
+ }
+
if( value->GetType() == TreeNode::OBJECT )
{
output << "}";
- if(indent)
- {
- output << std::endl;
- }
}
else
{
output << "]";
- if(indent)
- {
- output << std::endl;
- }
}
+
+ if( NULL != value->mNextSibling )
+ {
+ output << ",";
+ }
+
+ if( !groupChildren )
+ {
+ output << std::endl;
+ }
+
+ groupChildren = false;
break;
}
case TreeNode::STRING:
{
- output << "\"" << value->GetString() << "\"";
+ std::string escapedString = EscapeQuotes(value->GetString());
+ output << "\"" << escapedString << "\"";
if(NULL != value->mNextSibling)
{
output << ",";
}
- if(indent)
+
+ if( groupChildren )
+ {
+ output << " ";
+ }
+ else
{
output << std::endl;
}
-
break;
}
case TreeNode::INTEGER:
{
output << ",";
}
- if(indent)
+
+ if( groupChildren )
+ {
+ output << " ";
+ }
+ else
{
output << std::endl;
}
-
break;
}
case TreeNode::FLOAT:
{
output << ",";
}
- if(indent)
+
+ if( groupChildren )
+ {
+ output << " ";
+ }
+ else
{
output << std::endl;
}
{
output << "false";
}
+
if(NULL != value->mNextSibling)
{
output << ",";
}
- if(indent)
+
+ if( groupChildren )
+ {
+ output << " ";
+ }
+ else
{
output << std::endl;
}
} // namespace Toolkit
} // namespace Dali
-
/*
* Do write to string stream
*/
- void DoWrite(const TreeNode *value, std::ostream& output, int ident) const;
+ void DoWrite(const TreeNode *value, std::ostream& output, int level, int ident, bool groupChildren) const;
};
}
}
-void BubbleEmitter::SetBlendMode( bool enable )
-{
- if(enable)
- {
- // linear overlay
- mMaterial.SetBlendFunc(BlendingFactor::SRC_ALPHA, BlendingFactor::ONE,
- BlendingFactor::ZERO, BlendingFactor::ONE);
- }
- else
- {
- // using default blend func
- mMaterial.SetBlendFunc( BlendingFactor::SRC_ALPHA, BlendingFactor::ONE_MINUS_SRC_ALPHA,
- BlendingFactor::ONE, BlendingFactor::ONE_MINUS_SRC_ALPHA );
- }
-}
-
// clear the resources created for the off screen rendering
void BubbleEmitter::OnRenderFinished(RenderTask& source)
{
void SetBubbleDensity( unsigned int density );
/**
- * @copydoc Toolkit::BubbleEmitter::SetBlendMode
- */
- void SetBlendMode( bool enable );
-
- /**
* @copydoc Toolkit::BubbleEmitter::EmitBubble
*/
void EmitBubble( Animation& animation, const Vector2& emitPosition, const Vector2& direction, const Vector2& displacement );
DALI_TYPE_REGISTRATION_BEGIN( Toolkit::ImageView, Toolkit::Control, Create );
DALI_PROPERTY_REGISTRATION( Toolkit, ImageView, "resourceUrl", STRING, RESOURCE_URL )
DALI_PROPERTY_REGISTRATION( Toolkit, ImageView, "image", MAP, IMAGE )
+DALI_PROPERTY_REGISTRATION( Toolkit, ImageView, "preMultipliedAlpha", BOOLEAN, PRE_MULTIPLIED_ALPHA )
+
+DALI_ANIMATABLE_PROPERTY_REGISTRATION_WITH_DEFAULT( Toolkit, ImageView, "pixelArea", Vector4(0.f, 0.f, 1.f, 1.f), PIXEL_AREA )
DALI_TYPE_REGISTRATION_END()
} // anonymous namespace
using namespace Dali;
ImageView::ImageView()
-: Control( ControlBehaviour( ACTOR_BEHAVIOUR_NONE ) )
+: Control( ControlBehaviour( ACTOR_BEHAVIOUR_NONE ) ),
+ mPremultipledAlphaEnabled( false )
{
}
}
}
+void ImageView::EnablePreMultipliedAlpha( bool preMultipled )
+{
+ mPremultipledAlphaEnabled = preMultipled;
+
+ if( mRenderer )
+ {
+ ControlRenderer& rendererImpl = GetImplementation( mRenderer );
+ if (&typeid( rendererImpl ) == &typeid(ImageRenderer) )
+ {
+ ImageRenderer* imageRenderer = static_cast<ImageRenderer*>( &rendererImpl );
+ imageRenderer->EnablePreMultipliedAlpha( preMultipled );
+ }
+ }
+}
+
+bool ImageView::IsPreMultipliedAlphaEnabled() const
+{
+ return mPremultipledAlphaEnabled;
+}
+
void ImageView::SetDepthIndex( int depthIndex )
{
- mRenderer.SetDepthIndex( depthIndex );
+ if( mRenderer )
+ {
+ mRenderer.SetDepthIndex( depthIndex );
+ }
}
Vector3 ImageView::GetNaturalSize()
size.x = mImageSize.GetWidth();
size.y = mImageSize.GetHeight();
- size.z = std::min(size.x, size.y);
if( size.x > 0 && size.y > 0 )
{
+ size.z = std::min(size.x, size.y);
return size;
}
else
}
}
+
///////////////////////////////////////////////////////////
//
// Private methods
Control::OnStageDisconnection();
}
-
///////////////////////////////////////////////////////////
//
// Properties
break;
}
+
+ case Toolkit::ImageView::Property::PRE_MULTIPLIED_ALPHA:
+ {
+ bool IsPre;
+ if( value.Get( IsPre ) )
+ {
+ GetImpl(imageView).EnablePreMultipliedAlpha( IsPre );
+ }
+ break;
+ }
}
}
}
if ( imageview )
{
+ ImageView& impl = GetImpl( imageview );
switch ( propertyIndex )
{
case Toolkit::ImageView::Property::RESOURCE_URL:
{
- ImageView& impl = GetImpl( imageview );
if ( !impl.mUrl.empty() )
{
value = impl.mUrl;
case Toolkit::ImageView::Property::IMAGE:
{
- ImageView& impl = GetImpl( imageview );
if ( !impl.mUrl.empty() )
{
value = impl.mUrl;
}
break;
}
+
+ case Toolkit::ImageView::Property::PRE_MULTIPLIED_ALPHA:
+ {
+ value = impl.IsPreMultipliedAlphaEnabled();
+ break;
+ }
}
}
{
class ImageView : public Control
{
- protected:
+protected:
/**
* Construct a new ImageView.
*/
virtual ~ImageView();
-
-
public:
/**
* Create a new ImageView.
*/
void SetImage( const std::string& imageUrl, ImageDimensions size );
+ /**
+ * @brief Set whether the Pre-multiplied Alpha Blending is required
+ *
+ * @param[in] preMultipled whether alpha is pre-multiplied.
+ */
+ void EnablePreMultipliedAlpha( bool preMultipled );
+
+ /**
+ * @brief Query whether alpha is pre-multiplied.
+ *
+ * @return True is alpha is pre-multiplied, false otherwise.
+ */
+ bool IsPreMultipliedAlphaEnabled() const;
+
// Properties
/**
* Called when a property of an object of this type is set.
virtual float GetWidthForHeight( float height );
private:
- /**
- * Attaches mImage member to the renderer, creating the renderers, samplers, meshes and materials if needed
- *
- * @pre mImage has been initialised
- */
- void AttachImage();
-
-private:
// Undefined
ImageView( const ImageView& );
ImageView& operator=( const ImageView& );
std::string mUrl; ///< the url for the image if the image came from a URL, empty otherwise
Image mImage; ///< the Image if the image came from a Image, null otherwise
Property::Map mPropertyMap; ///< the Property::Map if the image came from a Property::Map, empty otherwise
+
+ bool mPremultipledAlphaEnabled; ///< Flag indicating whether the Pre-multiplied Alpha Blending is required
};
} // namespace Internal
mMaterial = Material::New( mShader );
- mMaterial.SetFaceCullingMode(Material::NONE);
-
if( mRenderer )
{
mRenderer.SetMaterial( mMaterial );
+ mRenderer.SetProperty( Renderer::Property::FACE_CULLING_MODE, Renderer::NONE);
}
UpdateShaderUniforms();
{\n
// flip the image horizontally by changing the x component of the texture coordinate
if( uIsBackImageVisible == 1.0 )\n
- gl_FragColor = texture2D( sTexture, vec2( uTextureRect.p+uTextureRect.s-vTexCoord.x, vTexCoord.y ) ) * uColor; \n
+ gl_FragColor = texture2D( sTexture, vec2( sTextureRect.p+sTextureRect.s-vTexCoord.x, vTexCoord.y ) ) * uColor; \n
else\n
gl_FragColor = texture2D( sTexture, vTexCoord ) * uColor;\n
// display book spine, a stripe of shadowed texture
- float pixelPos = (vTexCoord.x-uTextureRect.s)*uPageWidth; \n
+ float pixelPos = (vTexCoord.x-sTextureRect.s)*uPageWidth; \n
if(pixelPos < uSpineShadowParameter.x) \n
{\n
float x = pixelPos - uSpineShadowParameter.x;\n
\n
void main()\n
{\n
- vec4 position = vec4( aPosition*uSize.xy, 0.0, 1.0);\n
+ vec4 position = vec4( aPosition, 1.0);\n
vec2 currentCenter = vec2( uCommonParameters[1][2], uCommonParameters[1][3]);\n
vec2 originalCenter = vec2( uCommonParameters[0][2], uCommonParameters[0][3]);\n
vec3 normal = vec3(0.0,0.0,1.0);\n
}\n
gl_Position = uMvpMatrix * position;\n
// varying parameters for fragment shader
- vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5) );\n;
+ vTexCoord = mix( sTextureRect.xy, sTextureRect.zw, aTexCoord );\n;
vNormal = uNormalMatrix*normal;\n
vPosition = uModelView * position;\n
}\n
float spineShadowCoef = 1.0; \n
// display page content
// display back image of the page, flip the texture
- if( dot(vPosition.xyz, normal) > 0.0 ) texel = texture2D( sTexture, vec2( uTextureRect.p+uTextureRect.s-vTexCoord.x, vTexCoord.y ) );\n
+ if( dot(vPosition.xyz, normal) > 0.0 ) texel = texture2D( sTexture, vec2( sTextureRect.p+sTextureRect.s-vTexCoord.x, vTexCoord.y ) );\n
// display front image of the page
else texel = texture2D( sTexture, vTexCoord );\n
// display book spine, a stripe of shadowed texture
- float pixelPos = (vTexCoord.x-uTextureRect.s)*uPageSize.x; \n
+ float pixelPos = (vTexCoord.x-sTextureRect.s)*uPageSize.x; \n
if(pixelPos < uSpineShadowParameter.x) \n
{\n
float x = pixelPos - uSpineShadowParameter.x;\n
const char * const COLOR_NAME("borderColor");
const char * const SIZE_NAME("borderSize");
+const char * const ANTI_ALIASING("antiAliasing");
const char * const POSITION_ATTRIBUTE_NAME("aPosition");
const char * const DRIFT_ATTRIBUTE_NAME("aDrift");
gl_FragColor = borderColor*uColor;\n
}\n
);
+
+const char* VERTEX_SHADER_ANTI_ALIASING = DALI_COMPOSE_SHADER(
+ attribute mediump vec2 aPosition;\n
+ attribute mediump vec2 aDrift;\n
+ uniform mediump mat4 uMvpMatrix;\n
+ uniform mediump vec3 uSize;\n
+ uniform mediump float borderSize;\n
+ varying mediump float vAlpha;\n
+ \n
+ void main()\n
+ {\n
+ vec2 position = aPosition*(uSize.xy+vec2(0.75)) + aDrift*(borderSize+1.5);\n
+ gl_Position = uMvpMatrix * vec4(position, 0.0, 1.0);\n
+ vAlpha = min( abs(aDrift.x), abs(aDrift.y) )*(borderSize+1.5);
+ }\n
+);
+
+const char* FRAGMENT_SHADER_ANTI_ALIASING = DALI_COMPOSE_SHADER(
+ uniform lowp vec4 uColor;\n
+ uniform lowp vec4 borderColor;\n
+ uniform mediump float borderSize;\n
+ varying mediump float vAlpha;\n
+ \n
+ void main()\n
+ {\n
+ gl_FragColor = borderColor*uColor;\n
+ gl_FragColor.a *= smoothstep(0.0, 1.5, vAlpha)*smoothstep( borderSize+1.5, borderSize, vAlpha );\n
+ }\n
+);
}
BorderRenderer::BorderRenderer( RendererFactoryCache& factoryCache )
mBorderColor( Color::TRANSPARENT ),
mBorderSize( 0.f ),
mBorderColorIndex( Property::INVALID_INDEX ),
- mBorderSizeIndex( Property::INVALID_INDEX )
+ mBorderSizeIndex( Property::INVALID_INDEX ),
+ mAntiAliasing( false )
{
}
{
DALI_LOG_ERROR( "Fail to provide a border size to the BorderRenderer object" );
}
+
+ Property::Value* antiAliasing = propertyMap.Find( ANTI_ALIASING );
+ if( antiAliasing )
+ {
+ antiAliasing->Get( mAntiAliasing );
+ }
}
void BorderRenderer::SetClipRect( const Rect<int>& clipRect )
InitializeRenderer();
mBorderColorIndex = (mImpl->mRenderer).RegisterProperty( COLOR_NAME, mBorderColor );
- if( mBorderColor.a < 1.f )
+ if( mBorderColor.a < 1.f || mAntiAliasing)
{
- (mImpl->mRenderer).GetMaterial().SetBlendMode( BlendingMode::ON );
+ mImpl->mRenderer.SetProperty( Renderer::Property::BLENDING_MODE, BlendingMode::ON );
}
mBorderSizeIndex = (mImpl->mRenderer).RegisterProperty( SIZE_NAME, mBorderSize );
}
mFactoryCache.SaveGeometry( RendererFactoryCache::BORDER_GEOMETRY, geometry );
}
- Shader shader = mFactoryCache.GetShader( RendererFactoryCache::BORDER_SHADER );
- if( !shader )
- {
- shader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
- mFactoryCache.SaveShader( RendererFactoryCache::BORDER_SHADER, shader );
- }
-
- Material material = Material::New( shader );
+ Material material = Material::New( GetBorderShader() );
mImpl->mRenderer = Renderer::New( geometry, material );
}
if( mImpl->mRenderer )
{
(mImpl->mRenderer).SetProperty( mBorderColorIndex, color );
- if( color.a < 1.f && (mImpl->mRenderer).GetMaterial().GetBlendMode() != BlendingMode::ON)
+ if( color.a < 1.f )
{
- (mImpl->mRenderer).GetMaterial().SetBlendMode( BlendingMode::ON );
+ mImpl->mRenderer.SetProperty( Renderer::Property::BLENDING_MODE, BlendingMode::ON );
}
}
}
}
}
+void BorderRenderer::RequireAntiAliasing( bool antiAliasing )
+{
+ if( mAntiAliasing != antiAliasing )
+ {
+ mAntiAliasing = antiAliasing;
+ if( mImpl->mRenderer )
+ {
+ Material material = mImpl->mRenderer.GetMaterial();
+ Shader shader = GetBorderShader();
+ material.SetShader( shader );
+ if( mAntiAliasing )
+ {
+ mImpl->mRenderer.SetProperty( Renderer::Property::BLENDING_MODE, BlendingMode::ON );
+ }
+ }
+ }
+}
+
+Shader BorderRenderer::GetBorderShader()
+{
+ Shader shader;
+ if( mAntiAliasing )
+ {
+ shader = mFactoryCache.GetShader( RendererFactoryCache::BORDER_SHADER_ANTI_ALIASING );
+ if( !shader )
+ {
+ shader = Shader::New( VERTEX_SHADER_ANTI_ALIASING, FRAGMENT_SHADER_ANTI_ALIASING );
+ mFactoryCache.SaveShader( RendererFactoryCache::BORDER_SHADER_ANTI_ALIASING, shader );
+ }
+ }
+ else
+ {
+ shader = mFactoryCache.GetShader( RendererFactoryCache::BORDER_SHADER );
+ if( !shader )
+ {
+ shader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
+ mFactoryCache.SaveShader( RendererFactoryCache::BORDER_SHADER, shader );
+ }
+ }
+
+ return shader;
+}
+
/**
* Vertices and triangles of the border geometry:
*
* vertex position = aPosition*uSize.xy + aDrift*uBorderSize;
*
* 0--1--2--3
- * | /| /| /|
- * |/ |/ |/ |
+ * |\ | /| /|
+ * | \|/ |/ |
* 4--5--6--7
* |\ | |\ |
* | \| | \|
borderVertices.SetData(borderVertexData);
// Create indices
- unsigned int indexData[24] = { 0,4,1,5,2,6,3,7,7,6,11,10,15,14,14,10,13,9,12,8,8,9,4,5 };
+ unsigned int 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};
Property::Map indexFormat;
indexFormat[INDEX_NAME] = Property::INTEGER;
PropertyBuffer indices = PropertyBuffer::New( indexFormat, 24 );
* |-----------------|-------------|
* | borderColor | VECTOR4 |
* | borderSize | FLOAT |
+ * | antiAliasing | BOOLEAN |
*/
class BorderRenderer : public ControlRenderer
*/
void SetBorderSize( float size );
+ /**
+ * Enable/Disable the anti-aliasing.
+ * @param[in] enable Whether the anti-aliasing be enabled or not.
+ */
+ void RequireAntiAliasing( bool antiAliasing );
+
private:
/**
void InitializeRenderer();
/**
+ * Request the border shader from the factory cache. If fail, create tha shader and add it to cache.
+ * @return The border shader.
+ */
+ Shader GetBorderShader();
+
+ /**
* Create the geometry which presents the border.
* @return The border geometry
*/
Property::Index mBorderColorIndex;
Property::Index mBorderSizeIndex;
+
+ bool mAntiAliasing;
};
} // namespace Internal
mBlendColorIndex = mImpl->mRenderer.RegisterProperty( COLOR_NAME, mBlendColor );
if( mBlendColor.a < 1.f )
{
- mImpl->mRenderer.GetMaterial().SetBlendMode( BlendingMode::ON );
+ mImpl->mRenderer.SetProperty( Renderer::Property::BLENDING_MODE, BlendingMode::ON );
}
}
if( mImpl->mRenderer )
{
(mImpl->mRenderer).SetProperty( mBlendColorIndex, color );
- if( color.a < 1.f && (mImpl->mRenderer).GetMaterial().GetBlendMode() != BlendingMode::ON)
+ if( color.a < 1.f )
{
- (mImpl->mRenderer).GetMaterial().SetBlendMode( BlendingMode::ON );
+ mImpl->mRenderer.SetProperty( Renderer::Property::BLENDING_MODE, BlendingMode::ON );
}
}
}
mImpl->mDepthIndex = index;
if( mImpl->mRenderer )
{
- mImpl->mRenderer.SetDepthIndex( mImpl->mDepthIndex );
+ mImpl->mRenderer.SetProperty( Renderer::Property::DEPTH_INDEX, mImpl->mDepthIndex );
}
}
{
DoSetOnStage( actor );
- mImpl->mRenderer.SetDepthIndex( mImpl->mDepthIndex );
+ mImpl->mRenderer.SetProperty( Renderer::Property::DEPTH_INDEX, mImpl->mDepthIndex );
actor.AddRenderer( mImpl->mRenderer );
mImpl->mFlags |= Impl::IS_ON_STAGE;
}
// EXTERNAL HEADER
#include <cstring> // for strncasecmp
#include <dali/public-api/images/resource-image.h>
+#include <dali/public-api/images/native-image.h>
#include <dali/integration-api/debug.h>
// INTERNAL HEADER
const char * const DONT_CARE("dontCare");
const std::string TEXTURE_UNIFORM_NAME = "sTexture";
-const std::string TEXTURE_RECT_UNIFORM_NAME = "uTextureRect";
+const std::string ATLAS_RECT_UNIFORM_NAME = "uAtlasRect";
+const std::string PIXEL_AREA_UNIFORM_NAME = "pixelArea";
+
const Vector4 FULL_TEXTURE_RECT(0.f, 0.f, 1.f, 1.f);
+const char* DEFAULT_SAMPLER_TYPENAME = "sampler2D";
+
const char* VERTEX_SHADER = DALI_COMPOSE_SHADER(
attribute mediump vec2 aPosition;\n
- varying mediump vec2 vTexCoord;\n
uniform mediump mat4 uMvpMatrix;\n
uniform mediump vec3 uSize;\n
- uniform mediump vec4 uTextureRect;\n
+ uniform mediump vec4 uAtlasRect;\n
+ uniform mediump vec4 pixelArea;
+ varying mediump vec2 vTexCoord;\n
\n
void main()\n
{\n
vertexPosition.xyz *= uSize;\n
vertexPosition = uMvpMatrix * vertexPosition;\n
\n
- vTexCoord = mix( uTextureRect.xy, uTextureRect.zw, aPosition + vec2(0.5));\n
+ vTexCoord = mix( uAtlasRect.xy, uAtlasRect.zw, pixelArea.xy+pixelArea.zw*(aPosition + vec2(0.5) ) );\n
gl_Position = vertexPosition;\n
}\n
);
}\n
);
+
Geometry GenerateGeometry( const Vector< Vector2 >& vertices, const Vector< unsigned int >& indices )
{
Property::Map vertexFormat;
ImageRenderer::ImageRenderer( RendererFactoryCache& factoryCache, ImageAtlasManager& atlasManager )
: ControlRenderer( factoryCache ),
mAtlasManager( atlasManager ),
- mTextureRect( FULL_TEXTURE_RECT ),
mDesiredSize(),
mFittingMode( FittingMode::DEFAULT ),
- mSamplingMode( SamplingMode::DEFAULT )
+ mSamplingMode( SamplingMode::DEFAULT ),
+ mIsAlphaPreMultiplied( false ),
+ mNativeFragmentShaderCode( ),
+ mNativeImageFlag( false )
{
}
}
}
+ NativeImage nativeImage = NativeImage::DownCast( mImage );
+
+ if( nativeImage )
+ {
+ SetNativeFragmentShaderCode( nativeImage );
+ }
+
// if actor is on stage, create new renderer and apply to actor
if( actor && actor.OnStage() )
{
Geometry geometry;
Shader shader;
+ // If mImage is nativeImage with custom sampler or prefix, mNativeFragmentShaderCode will be applied.
+ // Renderer can't be shared between NativeImage and other image types.
+ if( !mNativeFragmentShaderCode.empty() )
+ {
+ return CreateNativeImageRenderer();
+ }
+
if( !mImpl->mCustomShader )
{
geometry = CreateGeometry( mFactoryCache, ImageDimensions( 1, 1 ) );
+
shader = GetImageShader(mFactoryCache);
}
else
shader = Shader::New( mImpl->mCustomShader->mVertexShader.empty() ? VERTEX_SHADER : mImpl->mCustomShader->mVertexShader,
mImpl->mCustomShader->mFragmentShader.empty() ? FRAGMENT_SHADER : mImpl->mCustomShader->mFragmentShader,
mImpl->mCustomShader->mHints );
+ if( mImpl->mCustomShader->mVertexShader.empty() )
+ {
+ shader.RegisterProperty( ATLAS_RECT_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ shader.RegisterProperty( PIXEL_AREA_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ }
+ }
+ }
+
+ Material material = Material::New( shader );
+ return Renderer::New( geometry, material );
+}
+
+Renderer ImageRenderer::CreateNativeImageRenderer() const
+{
+ Geometry geometry;
+ Shader shader;
+
+ if( !mImpl->mCustomShader )
+ {
+ geometry = CreateGeometry( mFactoryCache, ImageDimensions( 1, 1 ) );
+
+ shader = Shader::New( VERTEX_SHADER, mNativeFragmentShaderCode );
+ shader.RegisterProperty( ATLAS_RECT_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ shader.RegisterProperty( PIXEL_AREA_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ }
+ else
+ {
+ geometry = CreateGeometry( mFactoryCache, mImpl->mCustomShader->mGridSize );
+ if( mImpl->mCustomShader->mVertexShader.empty() && mImpl->mCustomShader->mFragmentShader.empty() )
+ {
+ shader = Shader::New( VERTEX_SHADER, mNativeFragmentShaderCode );
+ }
+ else
+ {
+ shader = Shader::New( mImpl->mCustomShader->mVertexShader.empty() ? VERTEX_SHADER : mImpl->mCustomShader->mVertexShader,
+ mNativeFragmentShaderCode,
+ mImpl->mCustomShader->mHints );
+ if( mImpl->mCustomShader->mVertexShader.empty() )
+ {
+ shader.RegisterProperty( ATLAS_RECT_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ shader.RegisterProperty( PIXEL_AREA_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ }
}
}
mImpl->mRenderer = mFactoryCache.GetRenderer( imageUrl );
if( !mImpl->mRenderer )
{
- Material material = mAtlasManager.Add(mTextureRect, imageUrl, mDesiredSize, mFittingMode, mSamplingMode );
+ Vector4 atlasRect;
+ Material material = mAtlasManager.Add(atlasRect, imageUrl, mDesiredSize, mFittingMode, mSamplingMode );
if( material )
{
Geometry geometry = CreateGeometry( mFactoryCache, ImageDimensions( 1, 1 ) );
mImpl->mRenderer = Renderer::New( geometry, material );
- SetTextureRectUniform(mTextureRect);
+ mImpl->mRenderer.RegisterProperty( ATLAS_RECT_UNIFORM_NAME, atlasRect );
}
else // big image, atlasing is not applied
{
mImpl->mRenderer = CreateRenderer();
- mTextureRect = FULL_TEXTURE_RECT;
- SetTextureRectUniform(mTextureRect);
- ResourceImage image = Dali::ResourceImage::New( imageUrl );
+ ResourceImage image = Dali::ResourceImage::New( imageUrl, mDesiredSize, mFittingMode, mSamplingMode );
image.LoadingFinishedSignal().Connect( this, &ImageRenderer::OnImageLoaded );
Material material = mImpl->mRenderer.GetMaterial();
material.AddTexture( image, TEXTURE_UNIFORM_NAME );
mFactoryCache.SaveRenderer( imageUrl, mImpl->mRenderer );
}
- else
- {
- Property::Value textureRect = mImpl->mRenderer.GetProperty( mImpl->mRenderer.GetPropertyIndex(TEXTURE_RECT_UNIFORM_NAME) );
- textureRect.Get( mTextureRect );
- }
+
mImpl->mFlags |= Impl::IS_FROM_CACHE;
}
else
ResourceImage resourceImage = Dali::ResourceImage::New( imageUrl, mDesiredSize, mFittingMode, mSamplingMode );
resourceImage.LoadingFinishedSignal().Connect( this, &ImageRenderer::OnImageLoaded );
ApplyImageToSampler( resourceImage );
-
- // custom vertex shader does not need texture rect uniform
- if( mImpl->mCustomShader && !mImpl->mCustomShader->mVertexShader.empty() )
- {
- return;
- }
-
- mTextureRect = FULL_TEXTURE_RECT;
- SetTextureRectUniform( mTextureRect );
}
}
{
ApplyImageToSampler( image );
}
-
- // default shader or custom shader with the default image vertex shader
- if( !mImpl->mCustomShader || mImpl->mCustomShader->mVertexShader.empty() )
- {
- mTextureRect = FULL_TEXTURE_RECT;
- SetTextureRectUniform( mTextureRect );
- }
}
{
InitializeRenderer( mImage );
}
+
+ mImpl->mRenderer.SetProperty(Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA, mIsAlphaPreMultiplied);
}
void ImageRenderer::DoSetOffStage( Actor& actor )
{
shader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
factoryCache.SaveShader( RendererFactoryCache::IMAGE_SHADER, shader );
+ shader.RegisterProperty( ATLAS_RECT_UNIFORM_NAME, FULL_TEXTURE_RECT );
+ shader.RegisterProperty( PIXEL_AREA_UNIFORM_NAME, FULL_TEXTURE_RECT );
}
return shader;
}
{
if( mImage != image )
{
+ NativeImage newNativeImage = NativeImage::DownCast( image );
+ bool newRendererFlag = true;
+
+ if( newNativeImage && !mNativeImageFlag )
+ {
+ SetNativeFragmentShaderCode( newNativeImage );
+ }
+
+ if( ( newNativeImage && mNativeImageFlag ) || ( !newNativeImage && !mNativeImageFlag ) )
+ {
+ newRendererFlag = false;
+ }
+
+ if( newNativeImage )
+ {
+ mNativeImageFlag = true;
+ }
+ else
+ {
+ mNativeFragmentShaderCode.clear();
+ mNativeImageFlag = false;
+ }
+
mImage = image;
if( mImpl->mRenderer )
{
- if( GetIsFromCache() ) // if renderer is from cache, remove the old one
+ // if renderer is from cache, remove the old one, and create new renderer
+ if( GetIsFromCache() )
{
//remove old renderer
if( actor )
SetOnStage(actor);
}
}
+ // if input image is nativeImage and mImage is regular image or the reverse, remove the old one, and create new renderer
+ else if( newRendererFlag )
+ {
+ //remove old renderer
+ if( actor )
+ {
+ actor.RemoveRenderer( mImpl->mRenderer );
+ }
+
+ if( actor && actor.OnStage() ) // if actor on stage, create a new renderer and apply to actor
+ {
+ SetOnStage(actor);
+ }
+ }
else // if renderer is not from cache, reuse the same renderer and only change the texture
{
ApplyImageToSampler( image );
}
}
+void ImageRenderer::EnablePreMultipliedAlpha( bool preMultipled )
+{
+ mIsAlphaPreMultiplied = preMultipled;
+ if( mImpl->mRenderer )
+ {
+ mImpl->mRenderer.SetProperty(Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA, mIsAlphaPreMultiplied);
+ }
+}
+
void ImageRenderer::ApplyImageToSampler( const Image& image )
{
if( image )
}
}
-void ImageRenderer::SetTextureRectUniform( const Vector4& textureRect )
+void ImageRenderer::CleanCache(const std::string& url)
{
- if( mImpl->mRenderer )
+ Material material = mImpl->mRenderer.GetMaterial();
+
+ Vector4 atlasRect( 0.f, 0.f, 1.f, 1.f );
+ Property::Index index = mImpl->mRenderer.GetPropertyIndex( ATLAS_RECT_UNIFORM_NAME );
+ if( index != Property::INVALID_INDEX )
{
- // Register/Set property.
- mImpl->mRenderer.RegisterProperty( TEXTURE_RECT_UNIFORM_NAME, textureRect );
+ Property::Value atlasRectValue = mImpl->mRenderer.GetProperty( index );
+ atlasRectValue.Get( atlasRect );
+ }
+
+ mImpl->mRenderer.Reset();
+ if( mFactoryCache.CleanRendererCache( url ) && index != Property::INVALID_INDEX )
+ {
+ mAtlasManager.Remove( material, atlasRect );
}
}
-void ImageRenderer::CleanCache(const std::string& url)
+void ImageRenderer::SetNativeFragmentShaderCode( Dali::NativeImage& nativeImage )
{
- Material material = mImpl->mRenderer.GetMaterial();
- mImpl->mRenderer.Reset();
- if( mFactoryCache.CleanRendererCache( url ) )
+ const char* fragmentPreFix = nativeImage.GetCustomFragmentPreFix();
+ const char* customSamplerTypename = nativeImage.GetCustomSamplerTypename();
+
+ if( fragmentPreFix )
{
- mAtlasManager.Remove( material, mTextureRect );
+ mNativeFragmentShaderCode = fragmentPreFix;
+ mNativeFragmentShaderCode += "\n";
}
+
+ if( mImpl->mCustomShader && !mImpl->mCustomShader->mFragmentShader.empty() )
+ {
+ mNativeFragmentShaderCode += mImpl->mCustomShader->mFragmentShader;
+ }
+ else
+ {
+ mNativeFragmentShaderCode += FRAGMENT_SHADER;
+ }
+
+ if( customSamplerTypename )
+ {
+ mNativeFragmentShaderCode.replace( mNativeFragmentShaderCode.find( DEFAULT_SAMPLER_TYPENAME ), strlen( DEFAULT_SAMPLER_TYPENAME ), customSamplerTypename );
+ }
+
}
} // namespace Internal
namespace Dali
{
+class NativeImage;
+
namespace Toolkit
{
*/
void SetImage( Actor& actor, const Image& image );
+ /**
+ * @brief Set whether the Pre-multiplied Alpha Blending is required
+ *
+ * @param[in] preMultipled whether alpha is pre-multiplied.
+ */
+ void EnablePreMultipliedAlpha( bool preMultipled );
+
private:
/**
Renderer CreateRenderer() const;
/**
+ * @brief Creates the Dali::Renderer for NativeImage with custom sampler type and prefix, initializing it
+ *
+ * @return Returns the created Dali::Renderer
+ */
+ Renderer CreateNativeImageRenderer() const;
+
+ /**
* Callback function of image resource loading succeed
* @param[in] image The Image content that we attempted to load from mImageUrl
*/
*/
void CleanCache(const std::string& url);
+ /**
+ * Set shader code for nativeimage if it exists
+ */
+ void SetNativeFragmentShaderCode( Dali::NativeImage& nativeImage );
+
private:
Image mImage;
ImageAtlasManager& mAtlasManager;
- Vector4 mTextureRect;
std::string mImageUrl;
Dali::ImageDimensions mDesiredSize;
Dali::FittingMode::Type mFittingMode;
Dali::SamplingMode::Type mSamplingMode;
+ bool mIsAlphaPreMultiplied;
+ std::string mNativeFragmentShaderCode;
+ bool mNativeImageFlag;
};
} // namespace Internal
{
COLOR_SHADER,
BORDER_SHADER,
+ BORDER_SHADER_ANTI_ALIASING,
GRADIENT_SHADER_LINEAR_USER_SPACE,
GRADIENT_SHADER_LINEAR_BOUNDING_BOX,
GRADIENT_SHADER_RADIAL_USER_SPACE,
}
}
-Toolkit::ControlRenderer RendererFactory::GetControlRenderer( float borderSize, const Vector4& borderColor )
+Toolkit::ControlRenderer RendererFactory::GetControlRenderer( float borderSize, const Vector4& borderColor, bool antiAliasing )
{
if( !mFactoryCache )
{
rendererPtr->SetBorderSize( borderSize );
rendererPtr->SetBorderColor( borderColor );
+ rendererPtr->RequireAntiAliasing( antiAliasing );
return Toolkit::ControlRenderer( rendererPtr );
}
}
renderer = GetControlRenderer( propertyMap );
- if( actor && actor.OnStage() )
+ if( renderer && actor && actor.OnStage() )
{
renderer.SetOnStage( actor );
}
void ResetRenderer( Toolkit::ControlRenderer& renderer, Actor& actor, const Vector4& color );
/**
- * @copydoc Toolkit::RenderFactory::GetControlRenderer( float, const Vector4& )
+ * @copydoc Toolkit::RenderFactory::GetControlRenderer( float, const Vector4&, bool )
*/
- Toolkit::ControlRenderer GetControlRenderer( float borderSize, const Vector4& borderColor );
+ Toolkit::ControlRenderer GetControlRenderer( float borderSize, const Vector4& borderColor, bool antiAliasing );
/**
* @copydoc Toolkit::RenderFactory::GetControlRenderer( const Image& )
namespace // Unnamed namespace
{
-//Type registration
-
-DALI_TYPE_REGISTRATION_BEGIN( Toolkit::ItemView, Toolkit::Scrollable, NULL)
-
-DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "layoutPosition", FLOAT, LAYOUT_POSITION)
-DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "scrollSpeed", FLOAT, SCROLL_SPEED)
-DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "overshoot", FLOAT, OVERSHOOT)
-DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "scrollDirection", VECTOR2, SCROLL_DIRECTION)
-DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "layoutOrientation", INTEGER, LAYOUT_ORIENTATION)
-DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "scrollContentSize", FLOAT, SCROLL_CONTENT_SIZE)
-
-DALI_SIGNAL_REGISTRATION( Toolkit, ItemView, "layoutActivated", LAYOUT_ACTIVATED_SIGNAL )
-
-DALI_TYPE_REGISTRATION_END()
-
const float DEFAULT_MINIMUM_SWIPE_SPEED = 1.0f;
const float DEFAULT_MINIMUM_SWIPE_DISTANCE = 3.0f;
const float DEFAULT_WHEEL_SCROLL_DISTANCE_STEP_PROPORTION = 0.1f;
namespace // unnamed namespace
{
+//Type registration
+
+DALI_TYPE_REGISTRATION_BEGIN( Toolkit::ItemView, Toolkit::Scrollable, NULL)
+
+DALI_PROPERTY_REGISTRATION( Toolkit, ItemView, "minimumSwipeSpeed", FLOAT, MINIMUM_SWIPE_SPEED )
+DALI_PROPERTY_REGISTRATION( Toolkit, ItemView, "minimumSwipeDistance", FLOAT, MINIMUM_SWIPE_DISTANCE )
+DALI_PROPERTY_REGISTRATION( Toolkit, ItemView, "wheelScrollDistanceStep", FLOAT, WHEEL_SCROLL_DISTANCE_STEP )
+DALI_PROPERTY_REGISTRATION( Toolkit, ItemView, "snapToItemEnabled", BOOLEAN, SNAP_TO_ITEM_ENABLED )
+DALI_PROPERTY_REGISTRATION( Toolkit, ItemView, "refreshInterval", FLOAT, REFRESH_INTERVAL )
+
+DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "layoutPosition", FLOAT, LAYOUT_POSITION)
+DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "scrollSpeed", FLOAT, SCROLL_SPEED)
+DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "overshoot", FLOAT, OVERSHOOT)
+DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "scrollDirection", VECTOR2, SCROLL_DIRECTION)
+DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "layoutOrientation", INTEGER, LAYOUT_ORIENTATION)
+DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ItemView, "scrollContentSize", FLOAT, SCROLL_CONTENT_SIZE)
+
+DALI_SIGNAL_REGISTRATION( Toolkit, ItemView, "layoutActivated", LAYOUT_ACTIVATED_SIGNAL )
+
+DALI_TYPE_REGISTRATION_END()
+
bool FindById( const ItemContainer& items, ItemId id )
{
for( ConstItemIter iter = items.begin(); items.end() != iter; ++iter )
return connected;
}
+void ItemView::SetProperty( BaseObject* object, Property::Index index, const Property::Value& value )
+{
+ Toolkit::ItemView itemView = Toolkit::ItemView::DownCast( Dali::BaseHandle( object ) );
+
+ if( itemView )
+ {
+ ItemView& itemViewImpl( GetImpl( itemView ) );
+ switch( index )
+ {
+ case Toolkit::ItemView::Property::MINIMUM_SWIPE_SPEED:
+ {
+ itemViewImpl.SetMinimumSwipeSpeed( value.Get<float>() );
+ break;
+ }
+ case Toolkit::ItemView::Property::MINIMUM_SWIPE_DISTANCE:
+ {
+ itemViewImpl.SetMinimumSwipeDistance( value.Get<float>() );
+ break;
+ }
+ case Toolkit::ItemView::Property::WHEEL_SCROLL_DISTANCE_STEP:
+ {
+ itemViewImpl.SetWheelScrollDistanceStep( value.Get<float>() );
+ break;
+ }
+ case Toolkit::ItemView::Property::SNAP_TO_ITEM_ENABLED:
+ {
+ itemViewImpl.SetAnchoring( value.Get<bool>() );
+ break;
+ }
+ case Toolkit::ItemView::Property::REFRESH_INTERVAL:
+ {
+ itemViewImpl.SetRefreshInterval( value.Get<float>() );
+ break;
+ }
+ }
+ }
+}
+
+Property::Value ItemView::GetProperty( BaseObject* object, Property::Index index )
+{
+ Property::Value value;
+
+ Toolkit::ItemView itemView = Toolkit::ItemView::DownCast( Dali::BaseHandle( object ) );
+
+ if( itemView )
+ {
+ ItemView& itemViewImpl( GetImpl( itemView ) );
+ switch( index )
+ {
+ case Toolkit::ItemView::Property::MINIMUM_SWIPE_SPEED:
+ {
+ value = itemViewImpl.GetMinimumSwipeSpeed();
+ break;
+ }
+ case Toolkit::ItemView::Property::MINIMUM_SWIPE_DISTANCE:
+ {
+ value = itemViewImpl.GetMinimumSwipeDistance();
+ break;
+ }
+ case Toolkit::ItemView::Property::WHEEL_SCROLL_DISTANCE_STEP:
+ {
+ value = itemViewImpl.GetWheelScrollDistanceStep();
+ break;
+ }
+ case Toolkit::ItemView::Property::SNAP_TO_ITEM_ENABLED:
+ {
+ value = itemViewImpl.GetAnchoring();
+ break;
+ }
+ case Toolkit::ItemView::Property::REFRESH_INTERVAL:
+ {
+ value = itemViewImpl.GetRefreshInterval();
+ break;
+ }
+ }
+ }
+
+ return value;
+}
+
} // namespace Internal
} // namespace Toolkit
*/
static bool DoConnectSignal( BaseObject* object, ConnectionTrackerInterface* tracker, const std::string& signalName, FunctorDelegate* functor );
+ //properties
+
+ /**
+ * Called when a property of an object of this type is set.
+ * @param[in] object The object whose property is set.
+ * @param[in] index The property index.
+ * @param[in] value The new property value.
+ */
+ static void SetProperty( BaseObject* object, Property::Index index, const Property::Value& value );
+
+ /**
+ * Called to retrieve a property of an object of this type.
+ * @param[in] object The object whose property is to be retrieved.
+ * @param[in] index The property index.
+ * @return The current value of the property.
+ */
+ static Property::Value GetProperty( BaseObject* object, Property::Index index );
+
private:
/**
// Setup properties, signals and actions using the type-registry.
DALI_TYPE_REGISTRATION_BEGIN( Toolkit::ScrollView, Toolkit::Scrollable, Create )
+DALI_PROPERTY_REGISTRATION( Toolkit, ScrollView, "wrapEnabled", BOOLEAN, WRAP_ENABLED )
+DALI_PROPERTY_REGISTRATION( Toolkit, ScrollView, "panningEnabled", BOOLEAN, PANNING_ENABLED )
+DALI_PROPERTY_REGISTRATION( Toolkit, ScrollView, "axisAutoLockEnabled", BOOLEAN, AXIS_AUTO_LOCK_ENABLED )
+DALI_PROPERTY_REGISTRATION( Toolkit, ScrollView, "wheelScrollDistanceStep", VECTOR2, WHEEL_SCROLL_DISTANCE_STEP )
+
DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ScrollView, "scrollPosition", VECTOR2, SCROLL_POSITION)
DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, ScrollView, "scrollPrePosition", VECTOR2, SCROLL_PRE_POSITION)
DALI_ANIMATABLE_PROPERTY_COMPONENT_REGISTRATION( Toolkit, ScrollView, "scrollPrePositionX", SCROLL_PRE_POSITION_X, SCROLL_PRE_POSITION, 0)
}
}
+bool ScrollView::GetScrollSensitive()
+{
+ return mSensitive;
+}
+
void ScrollView::SetScrollSensitive(bool sensitive)
{
Actor self = Self();
mSnapOvershootAlphaFunction = alpha;
}
+float ScrollView::GetSnapOvershootDuration()
+{
+ return mSnapOvershootDuration;
+}
+
void ScrollView::SetSnapOvershootDuration(float duration)
{
mSnapOvershootDuration = duration;
}
+bool ScrollView::GetActorAutoSnap()
+{
+ return mActorAutoSnapEnabled;
+}
+
void ScrollView::SetActorAutoSnap(bool enable)
{
mActorAutoSnapEnabled = enable;
ApplyConstraintToBoundActors(constraint);
}
+void ScrollView::SetProperty( BaseObject* object, Property::Index index, const Property::Value& value )
+{
+ Toolkit::ScrollView scrollView = Toolkit::ScrollView::DownCast( Dali::BaseHandle( object ) );
+
+ if( scrollView )
+ {
+ ScrollView& scrollViewImpl( GetImpl( scrollView ) );
+ switch( index )
+ {
+ case Toolkit::ScrollView::Property::WRAP_ENABLED:
+ {
+ scrollViewImpl.SetWrapMode( value.Get<bool>() );
+ break;
+ }
+ case Toolkit::ScrollView::Property::PANNING_ENABLED:
+ {
+ scrollViewImpl.SetScrollSensitive( value.Get<bool>() );
+ break;
+ }
+ case Toolkit::ScrollView::Property::AXIS_AUTO_LOCK_ENABLED:
+ {
+ scrollViewImpl.SetAxisAutoLock( value.Get<bool>() );
+ break;
+ }
+ case Toolkit::ScrollView::Property::WHEEL_SCROLL_DISTANCE_STEP:
+ {
+ scrollViewImpl.SetWheelScrollDistanceStep( value.Get<Vector2>() );
+ break;
+ }
+ }
+ }
+}
+
+Property::Value ScrollView::GetProperty( BaseObject* object, Property::Index index )
+{
+ Property::Value value;
+
+ Toolkit::ScrollView scrollView = Toolkit::ScrollView::DownCast( Dali::BaseHandle( object ) );
+
+ if( scrollView )
+ {
+ ScrollView& scrollViewImpl( GetImpl( scrollView ) );
+ switch( index )
+ {
+ case Toolkit::ScrollView::Property::WRAP_ENABLED:
+ {
+ value = scrollViewImpl.GetWrapMode();
+ break;
+ }
+ case Toolkit::ScrollView::Property::PANNING_ENABLED:
+ {
+ value = scrollViewImpl.GetScrollSensitive();
+ break;
+ }
+ case Toolkit::ScrollView::Property::AXIS_AUTO_LOCK_ENABLED:
+ {
+ value = scrollViewImpl.GetAxisAutoLock();
+ break;
+ }
+ case Toolkit::ScrollView::Property::WHEEL_SCROLL_DISTANCE_STEP:
+ {
+ value = scrollViewImpl.GetWheelScrollDistanceStep();
+ break;
+ }
+ }
+ }
+
+ return value;
+}
+
} // namespace Internal
} // namespace Toolkit
void SetRulerY(RulerPtr ruler);
/**
+ * Retrieve the touch sensitivity.
+ *
+ * @return whether the touch sensitivity is true or false.
+ */
+ bool GetScrollSensitive();
+
+ /**
* @copydoc Toolkit::ScrollView::SetScrollSensitive
*/
void SetScrollSensitive(bool sensitive);
void SetSnapOvershootAlphaFunction(AlphaFunction alpha);
/**
+ * Retrieve the duartion of Snap Overshoot animation
+ *
+ * @return the duration.
+ */
+ float GetSnapOvershootDuration();
+
+ /**
* @copydoc Toolkit::ScrollView::SetSnapOvershootDuration
*/
void SetSnapOvershootDuration(float duration);
/**
+ * Retrieve whether Actor Auto-Snap mode is enabled or not.
+ *
+ * @return Actor Auto-Snap mode Enabled flag.
+ */
+ bool GetActorAutoSnap();
+
+ /**
* @copydoc Toolkit::ScrollView::SetActorAutoSnap
*/
void SetActorAutoSnap(bool enable);
*/
void SetOvershootEffectColor( const Vector4& color );
+ //properties
+
+ /**
+ * Called when a property of an object of this type is set.
+ * @param[in] object The object whose property is set.
+ * @param[in] index The property index.
+ * @param[in] value The new property value.
+ */
+ static void SetProperty( BaseObject* object, Property::Index index, const Property::Value& value );
+
+ /**
+ * Called to retrieve a property of an object of this type.
+ * @param[in] object The object whose property is to be retrieved.
+ * @param[in] index The property index.
+ * @return The current value of the property.
+ */
+ static Property::Value GetProperty( BaseObject* object, Property::Index index );
+
public: //Signals
/**
DALI_PROPERTY_REGISTRATION( Toolkit, Scrollable, "overshootEffectColor", VECTOR4, OVERSHOOT_EFFECT_COLOR )
DALI_PROPERTY_REGISTRATION( Toolkit, Scrollable, "overshootAnimationSpeed", FLOAT, OVERSHOOT_ANIMATION_SPEED )
-const int OVERSHOOT_SIZE = Dali::Toolkit::Scrollable::Property::OVERSHOOT_ANIMATION_SPEED + 1; // OVERSHOOT_SIZE is not public yet
+DALI_PROPERTY_REGISTRATION( Toolkit, Scrollable, "overshootEnabled", BOOLEAN, OVERSHOOT_ENABLED )
+const int OVERSHOOT_SIZE = Dali::Toolkit::Scrollable::Property::OVERSHOOT_ENABLED + 1; // OVERSHOOT_SIZE is not public yet
Dali::PropertyRegistration p1( typeRegistration, "overshootSize", OVERSHOOT_SIZE, Property::VECTOR2, Dali::Toolkit::Internal::Scrollable::SetProperty, Dali::Toolkit::Internal::Scrollable::GetProperty );
DALI_ANIMATABLE_PROPERTY_REGISTRATION( Toolkit, Scrollable, "scrollRelativePosition", VECTOR2, SCROLL_RELATIVE_POSITION)
scrollableImpl.SetOvershootAnimationSpeed( value.Get<float>() );
break;
}
+ case Toolkit::Scrollable::Property::OVERSHOOT_ENABLED:
+ {
+ scrollableImpl.SetOvershootEnabled( value.Get<bool>() );
+ break;
+ }
case OVERSHOOT_SIZE: // OVERSHOOT_SIZE is not public yet
{
Vector2 input;
value = scrollableImpl.GetOvershootAnimationSpeed();
break;
}
+ case Toolkit::Scrollable::Property::OVERSHOOT_ENABLED:
+ {
+ value = scrollableImpl.IsOvershootEnabled();
+ break;
+ }
case OVERSHOOT_SIZE: // OVERSHOOT_SIZE is not public yet
{
value = scrollableImpl.mOvershootSize;
--- /dev/null
+/*
+ * Copyright (c) 2016 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/controls/text-controls/text-editor-impl.h>
+
+// EXTERNAL INCLUDES
+#include <cstring>
+#include <limits>
+#include <dali/public-api/adaptor-framework/key.h>
+#include <dali/public-api/common/stage.h>
+#include <dali/public-api/images/resource-image.h>
+#include <dali/devel-api/adaptor-framework/virtual-keyboard.h>
+#include <dali/devel-api/object/type-registry-helper.h>
+#include <dali/integration-api/debug.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/public-api/text/rendering-backend.h>
+#include <dali-toolkit/devel-api/controls/control-depth-index-ranges.h>
+#include <dali-toolkit/internal/text/rendering/text-backend.h>
+#include <dali-toolkit/internal/text/text-font-style.h>
+#include <dali-toolkit/internal/text/text-view.h>
+#include <dali-toolkit/internal/styling/style-manager-impl.h>
+
+using namespace Dali::Toolkit::Text;
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Internal
+{
+
+namespace // unnamed namespace
+{
+
+#if defined(DEBUG_ENABLED)
+ Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Concise, true, "LOG_TEXT_CONTROLS");
+#endif
+
+ const unsigned int DEFAULT_RENDERING_BACKEND = Dali::Toolkit::Text::DEFAULT_RENDERING_BACKEND;
+} // unnamed namespace
+
+namespace
+{
+
+const Scripting::StringEnum HORIZONTAL_ALIGNMENT_STRING_TABLE[] =
+{
+ { "BEGIN", Toolkit::Text::LayoutEngine::HORIZONTAL_ALIGN_BEGIN },
+ { "CENTER", Toolkit::Text::LayoutEngine::HORIZONTAL_ALIGN_CENTER },
+ { "END", Toolkit::Text::LayoutEngine::HORIZONTAL_ALIGN_END },
+};
+const unsigned int HORIZONTAL_ALIGNMENT_STRING_TABLE_COUNT = sizeof( HORIZONTAL_ALIGNMENT_STRING_TABLE ) / sizeof( HORIZONTAL_ALIGNMENT_STRING_TABLE[0] );
+
+// Type registration
+BaseHandle Create()
+{
+ return Toolkit::TextEditor::New();
+}
+
+// Setup properties, signals and actions using the type-registry.
+DALI_TYPE_REGISTRATION_BEGIN( Toolkit::TextEditor, Toolkit::Control, Create );
+
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "renderingBackend", INTEGER, RENDERING_BACKEND )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "text", STRING, TEXT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "textColor", VECTOR4, TEXT_COLOR )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "fontFamily", STRING, FONT_FAMILY )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "fontStyle", STRING, FONT_STYLE )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "pointSize", FLOAT, POINT_SIZE )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "horizontalAlignment", STRING, HORIZONTAL_ALIGNMENT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "scrollThreshold", FLOAT, SCROLL_THRESHOLD )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "scrollSpeed", FLOAT, SCROLL_SPEED )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "primaryCursorColor", VECTOR4, PRIMARY_CURSOR_COLOR )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "secondaryCursorColor", VECTOR4, SECONDARY_CURSOR_COLOR )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "enableCursorBlink", BOOLEAN, ENABLE_CURSOR_BLINK )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "cursorBlinkInterval", FLOAT, CURSOR_BLINK_INTERVAL )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "cursorBlinkDuration", FLOAT, CURSOR_BLINK_DURATION )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "cursorWidth", INTEGER, CURSOR_WIDTH )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "grabHandleImage", STRING, GRAB_HANDLE_IMAGE )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "grabHandlePressedImage", STRING, GRAB_HANDLE_PRESSED_IMAGE )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHandleImageLeft", MAP, SELECTION_HANDLE_IMAGE_LEFT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHandleImageRight", MAP, SELECTION_HANDLE_IMAGE_RIGHT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHandlePressedImageLeft", MAP, SELECTION_HANDLE_PRESSED_IMAGE_LEFT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHandlePressedImageRight", MAP, SELECTION_HANDLE_PRESSED_IMAGE_RIGHT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHandleMarkerImageLeft", MAP, SELECTION_HANDLE_MARKER_IMAGE_LEFT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHandleMarkerImageRight", MAP, SELECTION_HANDLE_MARKER_IMAGE_RIGHT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "selectionHighlightColor", VECTOR4, SELECTION_HIGHLIGHT_COLOR )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "decorationBoundingBox", RECTANGLE, DECORATION_BOUNDING_BOX )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "enableMarkup", BOOLEAN, ENABLE_MARKUP )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "inputColor", VECTOR4, INPUT_COLOR )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "inputFontFamily", STRING, INPUT_FONT_FAMILY )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "inputFontStyle", STRING, INPUT_FONT_STYLE )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextEditor, "inputPointSize", FLOAT, INPUT_POINT_SIZE )
+
+DALI_SIGNAL_REGISTRATION( Toolkit, TextEditor, "textChanged", SIGNAL_TEXT_CHANGED )
+
+DALI_TYPE_REGISTRATION_END()
+
+} // namespace
+
+Toolkit::TextEditor TextEditor::New()
+{
+ // Create the implementation, temporarily owned by this handle on stack
+ IntrusivePtr< TextEditor > impl = new TextEditor();
+
+ // Pass ownership to CustomActor handle
+ Toolkit::TextEditor handle( *impl );
+
+ // Second-phase init of the implementation
+ // This can only be done after the CustomActor connection has been made...
+ impl->Initialize();
+
+ return handle;
+}
+
+void TextEditor::SetProperty( BaseObject* object, Property::Index index, const Property::Value& value )
+{
+ Toolkit::TextEditor textEditor = Toolkit::TextEditor::DownCast( Dali::BaseHandle( object ) );
+
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor SetProperty\n");
+
+
+ if( textEditor )
+ {
+ TextEditor& impl( GetImpl( textEditor ) );
+
+ switch( index )
+ {
+ case Toolkit::TextEditor::Property::RENDERING_BACKEND:
+ {
+ int backend = value.Get< int >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p RENDERING_BACKEND %d\n", impl.mController.Get(), backend );
+
+ if( impl.mRenderingBackend != backend )
+ {
+ impl.mRenderingBackend = backend;
+ impl.mRenderer.Reset();
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::TEXT:
+ {
+ if( impl.mController )
+ {
+ const std::string text = value.Get< std::string >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p TEXT %s\n", impl.mController.Get(), text.c_str() );
+
+ impl.mController->SetText( text );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::TEXT_COLOR:
+ {
+ if( impl.mController )
+ {
+ const Vector4 textColor = value.Get< Vector4 >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p TEXT_COLOR %f,%f,%f,%f\n", impl.mController.Get(), textColor.r, textColor.g, textColor.b, textColor.a );
+
+ if( impl.mController->GetTextColor() != textColor )
+ {
+ impl.mController->SetTextColor( textColor );
+ impl.mController->SetInputColor( textColor );
+ impl.mRenderer.Reset();
+ }
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::FONT_FAMILY:
+ {
+ if( impl.mController )
+ {
+ const std::string fontFamily = value.Get< std::string >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p FONT_FAMILY %s\n", impl.mController.Get(), fontFamily.c_str() );
+ impl.mController->SetDefaultFontFamily( fontFamily );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::FONT_STYLE:
+ {
+ SetFontStyleProperty( impl.mController, value, Text::FontStyle::DEFAULT );
+ break;
+ }
+ case Toolkit::TextEditor::Property::POINT_SIZE:
+ {
+ if( impl.mController )
+ {
+ const float pointSize = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p POINT_SIZE %f\n", impl.mController.Get(), pointSize );
+
+ if( !Equals( impl.mController->GetDefaultPointSize(), pointSize ) )
+ {
+ impl.mController->SetDefaultPointSize( pointSize );
+ }
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::HORIZONTAL_ALIGNMENT:
+ {
+ if( impl.mController )
+ {
+ const std::string alignStr = value.Get< std::string >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p HORIZONTAL_ALIGNMENT %s\n", impl.mController.Get(), alignStr.c_str() );
+
+ LayoutEngine::HorizontalAlignment alignment( LayoutEngine::HORIZONTAL_ALIGN_BEGIN );
+ if( Scripting::GetEnumeration< LayoutEngine::HorizontalAlignment >( alignStr.c_str(),
+ HORIZONTAL_ALIGNMENT_STRING_TABLE,
+ HORIZONTAL_ALIGNMENT_STRING_TABLE_COUNT,
+ alignment ) )
+ {
+ impl.mController->SetHorizontalAlignment( alignment );
+ }
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SCROLL_THRESHOLD:
+ {
+ const float threshold = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p SCROLL_THRESHOLD %f\n", impl.mController.Get(), threshold );
+
+ if( impl.mDecorator )
+ {
+ impl.mDecorator->SetScrollThreshold( threshold );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SCROLL_SPEED:
+ {
+ const float speed = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p SCROLL_SPEED %f\n", impl.mController.Get(), speed );
+
+ if( impl.mDecorator )
+ {
+ impl.mDecorator->SetScrollSpeed( speed );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::PRIMARY_CURSOR_COLOR:
+ {
+ if( impl.mDecorator )
+ {
+ const Vector4 color = value.Get< Vector4 >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p PRIMARY_CURSOR_COLOR %f,%f,%f,%f\n", impl.mController.Get(), color.r, color.g, color.b, color.a );
+
+ impl.mDecorator->SetCursorColor( PRIMARY_CURSOR, color );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SECONDARY_CURSOR_COLOR:
+ {
+ if( impl.mDecorator )
+ {
+ const Vector4 color = value.Get< Vector4 >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p SECONDARY_CURSOR_COLOR %f,%f,%f,%f\n", impl.mController.Get(), color.r, color.g, color.b, color.a );
+
+ impl.mDecorator->SetCursorColor( SECONDARY_CURSOR, color );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::ENABLE_CURSOR_BLINK:
+ {
+ if( impl.mController )
+ {
+ const bool enable = value.Get< bool >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p ENABLE_CURSOR_BLINK %d\n", impl.mController.Get(), enable );
+
+ impl.mController->SetEnableCursorBlink( enable );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::CURSOR_BLINK_INTERVAL:
+ {
+ if( impl.mDecorator )
+ {
+ const float interval = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p CURSOR_BLINK_INTERVAL %f\n", impl.mController.Get(), interval );
+
+ impl.mDecorator->SetCursorBlinkInterval( interval );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::CURSOR_BLINK_DURATION:
+ {
+ if( impl.mDecorator )
+ {
+ const float duration = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p CURSOR_BLINK_DURATION %f\n", impl.mController.Get(), duration );
+
+ impl.mDecorator->SetCursorBlinkDuration( duration );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::CURSOR_WIDTH:
+ {
+ if( impl.mDecorator )
+ {
+ const int width = value.Get< int >();
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p CURSOR_WIDTH %d\n", impl.mController.Get(), width );
+
+ impl.mDecorator->SetCursorWidth( width );
+ impl.mController->GetLayoutEngine().SetCursorWidth( width );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::GRAB_HANDLE_IMAGE:
+ {
+ const ResourceImage image = ResourceImage::New( value.Get< std::string >() );
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p GRAB_HANDLE_IMAGE %s\n", impl.mController.Get(), image.GetUrl().c_str() );
+
+ if( impl.mDecorator )
+ {
+ impl.mDecorator->SetHandleImage( GRAB_HANDLE, HANDLE_IMAGE_RELEASED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::GRAB_HANDLE_PRESSED_IMAGE:
+ {
+ const ResourceImage image = ResourceImage::New( value.Get< std::string >() );
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor %p GRAB_HANDLE_PRESSED_IMAGE %s\n", impl.mController.Get(), image.GetUrl().c_str() );
+
+ if( impl.mDecorator )
+ {
+ impl.mDecorator->SetHandleImage( GRAB_HANDLE, HANDLE_IMAGE_PRESSED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_IMAGE_LEFT:
+ {
+ const Image image = Scripting::NewImage( value );
+
+ if( impl.mDecorator && image )
+ {
+ impl.mDecorator->SetHandleImage( LEFT_SELECTION_HANDLE, HANDLE_IMAGE_RELEASED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_IMAGE_RIGHT:
+ {
+ const Image image = Scripting::NewImage( value );
+
+ if( impl.mDecorator && image )
+ {
+ impl.mDecorator->SetHandleImage( RIGHT_SELECTION_HANDLE, HANDLE_IMAGE_RELEASED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_LEFT:
+ {
+ const Image image = Scripting::NewImage( value );
+
+ if( impl.mDecorator && image )
+ {
+ impl.mDecorator->SetHandleImage( LEFT_SELECTION_HANDLE, HANDLE_IMAGE_PRESSED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_RIGHT:
+ {
+ const Image image = Scripting::NewImage( value );
+
+ if( impl.mDecorator && image )
+ {
+ impl.mDecorator->SetHandleImage( RIGHT_SELECTION_HANDLE, HANDLE_IMAGE_PRESSED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_LEFT:
+ {
+ const Image image = Scripting::NewImage( value );
+
+ if( impl.mDecorator && image )
+ {
+ impl.mDecorator->SetHandleImage( LEFT_SELECTION_HANDLE_MARKER, HANDLE_IMAGE_RELEASED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_RIGHT:
+ {
+ const Image image = Scripting::NewImage( value );
+
+ if( impl.mDecorator && image )
+ {
+ impl.mDecorator->SetHandleImage( RIGHT_SELECTION_HANDLE_MARKER, HANDLE_IMAGE_RELEASED, image );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HIGHLIGHT_COLOR:
+ {
+ const Vector4 color = value.Get< Vector4 >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p SELECTION_HIGHLIGHT_COLOR %f,%f,%f,%f\n", impl.mController.Get(), color.r, color.g, color.b, color.a );
+
+ if( impl.mDecorator )
+ {
+ impl.mDecorator->SetHighlightColor( color );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::DECORATION_BOUNDING_BOX:
+ {
+ if( impl.mDecorator )
+ {
+ const Rect<int> box = value.Get< Rect<int> >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p DECORATION_BOUNDING_BOX %d,%d %dx%d\n", impl.mController.Get(), box.x, box.y, box.width, box.height );
+
+ impl.mDecorator->SetBoundingBox( box );
+ impl.RequestTextRelayout();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::ENABLE_MARKUP:
+ {
+ if( impl.mController )
+ {
+ const bool enableMarkup = value.Get<bool>();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p ENABLE_MARKUP %d\n", impl.mController.Get(), enableMarkup );
+
+ impl.mController->SetMarkupProcessorEnabled( enableMarkup );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_COLOR:
+ {
+ if( impl.mController )
+ {
+ const Vector4 inputColor = value.Get< Vector4 >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p INPUT_COLOR %f,%f,%f,%f\n", impl.mController.Get(), inputColor.r, inputColor.g, inputColor.b, inputColor.a );
+
+ impl.mController->SetInputColor( inputColor );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_FONT_FAMILY:
+ {
+ if( impl.mController )
+ {
+ const std::string fontFamily = value.Get< std::string >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p INPUT_FONT_FAMILY %s\n", impl.mController.Get(), fontFamily.c_str() );
+ impl.mController->SetInputFontFamily( fontFamily );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_FONT_STYLE:
+ {
+ SetFontStyleProperty( impl.mController, value, Text::FontStyle::INPUT );
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_POINT_SIZE:
+ {
+ if( impl.mController )
+ {
+ const float pointSize = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p INPUT_POINT_SIZE %f\n", impl.mController.Get(), pointSize );
+ impl.mController->SetInputFontPointSize( pointSize );
+ }
+ break;
+ }
+ } // switch
+ } // texteditor
+}
+
+Property::Value TextEditor::GetProperty( BaseObject* object, Property::Index index )
+{
+ Property::Value value;
+
+ Toolkit::TextEditor textEditor = Toolkit::TextEditor::DownCast( Dali::BaseHandle( object ) );
+
+ if( textEditor )
+ {
+ TextEditor& impl( GetImpl( textEditor ) );
+
+ switch( index )
+ {
+ case Toolkit::TextEditor::Property::RENDERING_BACKEND:
+ {
+ value = impl.mRenderingBackend;
+ break;
+ }
+ case Toolkit::TextEditor::Property::TEXT:
+ {
+ if( impl.mController )
+ {
+ std::string text;
+ impl.mController->GetText( text );
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor %p returning text: %s\n", impl.mController.Get(), text.c_str() );
+ value = text;
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::TEXT_COLOR:
+ {
+ if ( impl.mController )
+ {
+ value = impl.mController->GetTextColor();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::FONT_FAMILY:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetDefaultFontFamily();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::FONT_STYLE:
+ {
+ GetFontStyleProperty( impl.mController, value, Text::FontStyle::DEFAULT );
+ break;
+ }
+ case Toolkit::TextEditor::Property::POINT_SIZE:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetDefaultPointSize();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::HORIZONTAL_ALIGNMENT:
+ {
+ if( impl.mController )
+ {
+ const char* name = Scripting::GetEnumerationName< Toolkit::Text::LayoutEngine::HorizontalAlignment >( impl.mController->GetLayoutEngine().GetHorizontalAlignment(),
+ HORIZONTAL_ALIGNMENT_STRING_TABLE,
+ HORIZONTAL_ALIGNMENT_STRING_TABLE_COUNT );
+ if( name )
+ {
+ value = std::string( name );
+ }
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SCROLL_THRESHOLD:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetScrollThreshold();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SCROLL_SPEED:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetScrollSpeed();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::PRIMARY_CURSOR_COLOR:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetColor( PRIMARY_CURSOR );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SECONDARY_CURSOR_COLOR:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetColor( SECONDARY_CURSOR );
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::ENABLE_CURSOR_BLINK:
+ {
+ value = impl.mController->GetEnableCursorBlink();
+ break;
+ }
+ case Toolkit::TextEditor::Property::CURSOR_BLINK_INTERVAL:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetCursorBlinkInterval();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::CURSOR_BLINK_DURATION:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetCursorBlinkDuration();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::CURSOR_WIDTH:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetCursorWidth();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::GRAB_HANDLE_IMAGE:
+ {
+ if( impl.mDecorator )
+ {
+ ResourceImage image = ResourceImage::DownCast( impl.mDecorator->GetHandleImage( GRAB_HANDLE, HANDLE_IMAGE_RELEASED ) );
+ if( image )
+ {
+ value = image.GetUrl();
+ }
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::GRAB_HANDLE_PRESSED_IMAGE:
+ {
+ if( impl.mDecorator )
+ {
+ ResourceImage image = ResourceImage::DownCast( impl.mDecorator->GetHandleImage( GRAB_HANDLE, HANDLE_IMAGE_PRESSED ) );
+ if( image )
+ {
+ value = image.GetUrl();
+ }
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_IMAGE_LEFT:
+ {
+ impl.GetHandleImagePropertyValue( value, LEFT_SELECTION_HANDLE, HANDLE_IMAGE_RELEASED );
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_IMAGE_RIGHT:
+ {
+ impl.GetHandleImagePropertyValue( value, RIGHT_SELECTION_HANDLE, HANDLE_IMAGE_RELEASED ) ;
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_LEFT:
+ {
+ impl.GetHandleImagePropertyValue( value, LEFT_SELECTION_HANDLE, HANDLE_IMAGE_PRESSED );
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_PRESSED_IMAGE_RIGHT:
+ {
+ impl.GetHandleImagePropertyValue( value, RIGHT_SELECTION_HANDLE, HANDLE_IMAGE_PRESSED );
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_LEFT:
+ {
+ impl.GetHandleImagePropertyValue( value, LEFT_SELECTION_HANDLE_MARKER, HANDLE_IMAGE_RELEASED );
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HANDLE_MARKER_IMAGE_RIGHT:
+ {
+ impl.GetHandleImagePropertyValue( value, RIGHT_SELECTION_HANDLE_MARKER, HANDLE_IMAGE_RELEASED );
+ break;
+ }
+ case Toolkit::TextEditor::Property::SELECTION_HIGHLIGHT_COLOR:
+ {
+ if( impl.mDecorator )
+ {
+ value = impl.mDecorator->GetHighlightColor();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::DECORATION_BOUNDING_BOX:
+ {
+ if( impl.mDecorator )
+ {
+ Rect<int> boundingBox;
+ impl.mDecorator->GetBoundingBox( boundingBox );
+ value = boundingBox;
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::ENABLE_MARKUP:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->IsMarkupProcessorEnabled();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_COLOR:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetInputColor();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_FONT_FAMILY:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetInputFontFamily();
+ }
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_FONT_STYLE:
+ {
+ GetFontStyleProperty( impl.mController, value, Text::FontStyle::INPUT );
+ break;
+ }
+ case Toolkit::TextEditor::Property::INPUT_POINT_SIZE:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetInputFontPointSize();
+ }
+ break;
+ }
+ } //switch
+ }
+
+ return value;
+}
+
+bool TextEditor::DoConnectSignal( BaseObject* object, ConnectionTrackerInterface* tracker, const std::string& signalName, FunctorDelegate* functor )
+{
+ Dali::BaseHandle handle( object );
+
+ bool connected( true );
+ Toolkit::TextEditor editor = Toolkit::TextEditor::DownCast( handle );
+
+ if( 0 == strcmp( signalName.c_str(), SIGNAL_TEXT_CHANGED ) )
+ {
+ editor.TextChangedSignal().Connect( tracker, functor );
+ }
+ else
+ {
+ // signalName does not match any signal
+ connected = false;
+ }
+
+ return connected;
+}
+
+Toolkit::TextEditor::TextChangedSignalType& TextEditor::TextChangedSignal()
+{
+ return mTextChangedSignal;
+}
+
+void TextEditor::OnInitialize()
+{
+ Actor self = Self();
+
+ mController = Text::Controller::New( *this );
+
+ mDecorator = Text::Decorator::New( *mController,
+ *mController );
+
+ mController->GetLayoutEngine().SetLayout( LayoutEngine::MULTI_LINE_BOX );
+
+ mController->EnableTextInput( mDecorator );
+
+ mController->SetMaximumNumberOfCharacters( std::numeric_limits<Length>::max() );
+
+ // Forward input events to controller
+ EnableGestureDetection( static_cast<Gesture::Type>( Gesture::Tap | Gesture::Pan | Gesture::LongPress ) );
+ GetTapGestureDetector().SetMaximumTapsRequired( 2 );
+
+ self.TouchedSignal().Connect( this, &TextEditor::OnTouched );
+
+ // Set BoundingBox to stage size if not already set.
+ Rect<int> boundingBox;
+ mDecorator->GetBoundingBox( boundingBox );
+
+ if( boundingBox.IsEmpty() )
+ {
+ Vector2 stageSize = Dali::Stage::GetCurrent().GetSize();
+ mDecorator->SetBoundingBox( Rect<int>( 0.0f, 0.0f, stageSize.width, stageSize.height ) );
+ }
+
+ // Flip vertically the 'left' selection handle
+ mDecorator->FlipHandleVertically( LEFT_SELECTION_HANDLE, true );
+
+ // Fill-parent area by default
+ self.SetResizePolicy( ResizePolicy::FILL_TO_PARENT, Dimension::WIDTH );
+ self.SetResizePolicy( ResizePolicy::FILL_TO_PARENT, Dimension::HEIGHT );
+ self.OnStageSignal().Connect( this, &TextEditor::OnStageConnect );
+}
+
+void TextEditor::OnStyleChange( Toolkit::StyleManager styleManager, StyleChange::Type change )
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnStyleChange\n");
+
+ switch ( change )
+ {
+ case StyleChange::DEFAULT_FONT_CHANGE:
+ {
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnStyleChange DEFAULT_FONT_CHANGE\n");
+ std::string newFont = styleManager.GetDefaultFontFamily();
+ // Property system did not set the font so should update it.
+ mController->UpdateAfterFontChange( newFont );
+ break;
+ }
+
+ case StyleChange::DEFAULT_FONT_SIZE_CHANGE:
+ {
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextEditor::OnStyleChange StyleChange::DEFAULT_FONT_SIZE_CHANGE (%f)\n", mController->GetDefaultPointSize() );
+
+ if ( (mController->GetDefaultPointSize() <= 0.0f) ) // If DefaultPointSize not set by Property system it will be 0.0f
+ {
+ // Property system did not set the PointSize so should update it.
+ // todo instruct text-controller to update model
+ }
+ break;
+ }
+ case StyleChange::THEME_CHANGE:
+ {
+ GetImpl( styleManager ).ApplyThemeStyle( Toolkit::Control( GetOwner() ) );
+ break;
+ }
+ }
+}
+
+Vector3 TextEditor::GetNaturalSize()
+{
+ return mController->GetNaturalSize();
+}
+
+float TextEditor::GetHeightForWidth( float width )
+{
+ return mController->GetHeightForWidth( width );
+}
+
+void TextEditor::OnRelayout( const Vector2& size, RelayoutContainer& container )
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor OnRelayout\n");
+
+ if( mController->Relayout( size ) ||
+ !mRenderer )
+ {
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnRelayout %p Displaying new contents\n", mController.Get() );
+
+ if( mDecorator )
+ {
+ mDecorator->Relayout( size );
+ }
+
+ if( !mRenderer )
+ {
+ mRenderer = Backend::Get().NewRenderer( mRenderingBackend );
+ }
+
+ EnableClipping( true, size );
+ RenderText();
+ }
+}
+
+void TextEditor::RenderText()
+{
+ Actor self = Self();
+ Actor renderableActor;
+ if( mRenderer )
+ {
+ renderableActor = mRenderer->Render( mController->GetView(), DepthIndex::TEXT );
+ }
+
+ if( renderableActor != mRenderableActor )
+ {
+ UnparentAndReset( mRenderableActor );
+ mRenderableActor = renderableActor;
+ }
+
+ if( mRenderableActor )
+ {
+ const Vector2 offset = mController->GetScrollPosition() + mController->GetAlignmentOffset();
+
+ mRenderableActor.SetPosition( offset.x, offset.y );
+
+ Actor clipRootActor;
+ if( mClipper )
+ {
+ clipRootActor = mClipper->GetRootActor();
+ }
+
+ for( std::vector<Actor>::const_iterator it = mClippingDecorationActors.begin(),
+ endIt = mClippingDecorationActors.end();
+ it != endIt;
+ ++it )
+ {
+ Actor actor = *it;
+
+ if( clipRootActor )
+ {
+ clipRootActor.Add( actor );
+ }
+ else
+ {
+ self.Add( actor );
+ }
+ }
+ mClippingDecorationActors.clear();
+
+ // Make sure the actor is parented correctly with/without clipping
+ if( clipRootActor )
+ {
+ clipRootActor.Add( mRenderableActor );
+ }
+ else
+ {
+ self.Add( mRenderableActor );
+ }
+ }
+}
+
+void TextEditor::OnKeyInputFocusGained()
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnKeyInputFocusGained %p\n", mController.Get() );
+
+ VirtualKeyboard::StatusChangedSignal().Connect( this, &TextEditor::KeyboardStatusChanged );
+
+ ImfManager imfManager = ImfManager::Get();
+
+ if ( imfManager )
+ {
+ imfManager.EventReceivedSignal().Connect( this, &TextEditor::OnImfEvent );
+
+ // Notify that the text editing start.
+ imfManager.Activate();
+
+ // When window gain lost focus, the imf manager is deactivated. Thus when window gain focus again, the imf manager must be activated.
+ imfManager.SetRestoreAfterFocusLost( true );
+ }
+
+ ClipboardEventNotifier notifier( ClipboardEventNotifier::Get() );
+
+ if ( notifier )
+ {
+ notifier.ContentSelectedSignal().Connect( this, &TextEditor::OnClipboardTextSelected );
+ }
+
+ mController->KeyboardFocusGainEvent(); // Called in the case of no virtual keyboard to trigger this event
+
+ EmitKeyInputFocusSignal( true ); // Calls back into the Control hence done last.
+}
+
+void TextEditor::OnKeyInputFocusLost()
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor:OnKeyInputFocusLost %p\n", mController.Get() );
+
+ VirtualKeyboard::StatusChangedSignal().Disconnect( this, &TextEditor::KeyboardStatusChanged );
+
+ ImfManager imfManager = ImfManager::Get();
+ if ( imfManager )
+ {
+ // The text editing is finished. Therefore the imf manager don't have restore activation.
+ imfManager.SetRestoreAfterFocusLost( false );
+
+ // Notify that the text editing finish.
+ imfManager.Deactivate();
+
+ imfManager.EventReceivedSignal().Disconnect( this, &TextEditor::OnImfEvent );
+ }
+
+ ClipboardEventNotifier notifier( ClipboardEventNotifier::Get() );
+
+ if ( notifier )
+ {
+ notifier.ContentSelectedSignal().Disconnect( this, &TextEditor::OnClipboardTextSelected );
+ }
+
+ mController->KeyboardFocusLostEvent();
+
+ EmitKeyInputFocusSignal( false ); // Calls back into the Control hence done last.
+}
+
+void TextEditor::OnTap( const TapGesture& gesture )
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnTap %p\n", mController.Get() );
+
+ // Show the keyboard if it was hidden.
+ if (!VirtualKeyboard::IsVisible())
+ {
+ VirtualKeyboard::Show();
+ }
+
+ // Deliver the tap before the focus event to controller; this allows us to detect when focus is gained due to tap-gestures
+ mController->TapEvent( gesture.numberOfTaps, gesture.localPoint.x, gesture.localPoint.y );
+
+ SetKeyInputFocus();
+}
+
+void TextEditor::OnPan( const PanGesture& gesture )
+{
+ mController->PanEvent( gesture.state, gesture.displacement );
+}
+
+void TextEditor::OnLongPress( const LongPressGesture& gesture )
+{
+ // Show the keyboard if it was hidden.
+ if (!VirtualKeyboard::IsVisible())
+ {
+ VirtualKeyboard::Show();
+ }
+
+ mController->LongPressEvent( gesture.state, gesture.localPoint.x, gesture.localPoint.y );
+
+ SetKeyInputFocus();
+}
+
+bool TextEditor::OnKeyEvent( const KeyEvent& event )
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnKeyEvent %p keyCode %d\n", mController.Get(), event.keyCode );
+
+ if( Dali::DALI_KEY_ESCAPE == event.keyCode ) // Make a Dali key code for this
+ {
+ ClearKeyInputFocus();
+ return true;
+ }
+
+ return mController->KeyEvent( event );
+}
+
+void TextEditor::AddDecoration( Actor& actor, bool needsClipping )
+{
+ if( actor )
+ {
+ if( needsClipping )
+ {
+ mClippingDecorationActors.push_back( actor );
+ }
+ else
+ {
+ Self().Add( actor );
+ }
+ }
+}
+
+void TextEditor::RequestTextRelayout()
+{
+ RelayoutRequest();
+}
+
+void TextEditor::TextChanged()
+{
+ Dali::Toolkit::TextEditor handle( GetOwner() );
+ mTextChangedSignal.Emit( handle );
+}
+
+void TextEditor::MaxLengthReached()
+{
+ // Nothing to do as TextEditor doesn't emit a max length reached signal.
+}
+
+void TextEditor::OnStageConnect( Dali::Actor actor )
+{
+ if ( mHasBeenStaged )
+ {
+ RenderText();
+ }
+ else
+ {
+ mHasBeenStaged = true;
+ }
+}
+
+ImfManager::ImfCallbackData TextEditor::OnImfEvent( Dali::ImfManager& imfManager, const ImfManager::ImfEventData& imfEvent )
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::OnImfEvent %p eventName %d\n", mController.Get(), imfEvent.eventName );
+ return mController->OnImfEvent( imfManager, imfEvent );
+}
+
+void TextEditor::GetHandleImagePropertyValue( Property::Value& value, Text::HandleType handleType, Text::HandleImageType handleImageType )
+{
+ if( mDecorator )
+ {
+ ResourceImage image = ResourceImage::DownCast( mDecorator->GetHandleImage( handleType, handleImageType ) );
+
+ if ( image )
+ {
+ Property::Map map;
+ Scripting::CreatePropertyMap( image, map );
+ value = map;
+ }
+ }
+}
+
+void TextEditor::EnableClipping( bool clipping, const Vector2& size )
+{
+ if( clipping )
+ {
+ // Not worth to created clip actor if width or height is equal to zero.
+ if( size.width > Math::MACHINE_EPSILON_1000 && size.height > Math::MACHINE_EPSILON_1000 )
+ {
+ if( !mClipper )
+ {
+ Actor self = Self();
+
+ mClipper = Clipper::New( size );
+ self.Add( mClipper->GetRootActor() );
+ self.Add( mClipper->GetImageActor() );
+ }
+ else if ( mClipper )
+ {
+ mClipper->Refresh( size );
+ }
+ }
+ }
+ else
+ {
+ // Note - this will automatically remove the root & image actors
+ mClipper.Reset();
+ }
+}
+
+void TextEditor::OnClipboardTextSelected( ClipboardEventNotifier& clipboard )
+{
+ mController->PasteClipboardItemEvent();
+}
+
+void TextEditor::KeyboardStatusChanged(bool keyboardShown)
+{
+ DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextEditor::KeyboardStatusChanged %p keyboardShown %d\n", mController.Get(), keyboardShown );
+
+ // Just hide the grab handle when keyboard is hidden.
+ if (!keyboardShown )
+ {
+ mController->KeyboardFocusLostEvent();
+ }
+ else
+ {
+ mController->KeyboardFocusGainEvent(); // Initially called by OnKeyInputFocusGained
+ }
+}
+
+void TextEditor::OnStageConnection( int depth )
+{
+ // Call the Control::OnStageConnection() to set the depth of the background.
+ Control::OnStageConnection( depth );
+
+ // Sets the depth to the renderers inside the text's decorator.
+ mDecorator->SetTextDepth( depth );
+
+ // The depth of the text renderer is set in the RenderText() called from OnRelayout().
+}
+
+bool TextEditor::OnTouched( Actor actor, const TouchEvent& event )
+{
+ return true;
+}
+
+TextEditor::TextEditor()
+: Control( ControlBehaviour( REQUIRES_STYLE_CHANGE_SIGNALS ) ),
+ mRenderingBackend( DEFAULT_RENDERING_BACKEND ),
+ mHasBeenStaged( false )
+{
+}
+
+TextEditor::~TextEditor()
+{
+ mClipper.Reset();
+}
+
+} // namespace Internal
+
+} // namespace Toolkit
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_TOOLKIT_INTERNAL_TEXT_EDITOR_H__
+#define __DALI_TOOLKIT_INTERNAL_TEXT_EDITOR_H__
+
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/public-api/controls/control-impl.h>
+#include <dali-toolkit/devel-api/controls/text-controls/text-editor.h>
+#include <dali-toolkit/internal/text/clipping/text-clipper.h>
+#include <dali-toolkit/internal/text/decorator/text-decorator.h>
+#include <dali-toolkit/internal/text/text-control-interface.h>
+#include <dali-toolkit/internal/text/text-controller.h>
+#include <dali-toolkit/internal/text/rendering/text-renderer.h>
+
+// EXTERNAL INCLUDES
+#include <dali/devel-api/adaptor-framework/clipboard-event-notifier.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Internal
+{
+
+/**
+ * @brief A control which renders a long text string with styles.
+ */
+class TextEditor : public Control, public Text::ControlInterface
+{
+public:
+
+ /**
+ * @copydoc Dali::Toollkit::TextEditor::New()
+ */
+ static Toolkit::TextEditor New();
+
+ // Properties
+
+ /**
+ * @brief Called when a property of an object of this type is set.
+ *
+ * @param[in] object The object whose property is set.
+ * @param[in] index The property index.
+ * @param[in] value The new property value.
+ */
+ static void SetProperty( BaseObject* object, Property::Index index, const Property::Value& value );
+
+ /**
+ * @brief Called to retrieve a property of an object of this type.
+ *
+ * @param[in] object The object whose property is to be retrieved.
+ * @param[in] index The property index.
+ * @return The current value of the property.
+ */
+ static Property::Value GetProperty( BaseObject* object, Property::Index index );
+
+ /**
+ * Connects a callback function with the object's signals.
+ * @param[in] object The object providing the signal.
+ * @param[in] tracker Used to disconnect the signal.
+ * @param[in] signalName The signal to connect to.
+ * @param[in] functor A newly allocated FunctorDelegate.
+ * @return True if the signal was connected.
+ * @post If a signal was connected, ownership of functor was passed to CallbackBase. Otherwise the caller is responsible for deleting the unused functor.
+ */
+ static bool DoConnectSignal( BaseObject* object, ConnectionTrackerInterface* tracker, const std::string& signalName, FunctorDelegate* functor );
+
+ /**
+ * @copydoc TextEditor::TextChangedSignal()
+ */
+ Toolkit::TextEditor::TextChangedSignalType& TextChangedSignal();
+
+private: // From Control
+
+ /**
+ * @copydoc Control::OnInitialize()
+ */
+ virtual void OnInitialize();
+
+ /**
+ * @copydoc Control::OnStyleChange()
+ */
+ virtual void OnStyleChange( Toolkit::StyleManager styleManager, StyleChange::Type change );
+
+ /**
+ * @copydoc Control::GetNaturalSize()
+ */
+ virtual Vector3 GetNaturalSize();
+
+ /**
+ * @copydoc Control::GetHeightForWidth()
+ */
+ virtual float GetHeightForWidth( float width );
+
+ /**
+ * @copydoc Control::OnInitialize()
+ */
+ virtual void OnRelayout( const Vector2& size, RelayoutContainer& container );
+
+ /**
+ * @copydoc Control::OnKeyInputFocusGained()
+ */
+ virtual void OnKeyInputFocusGained();
+
+ /**
+ * @copydoc Control::OnKeyInputFocusLost()
+ */
+ virtual void OnKeyInputFocusLost();
+
+ /**
+ * @copydoc Control::OnTap()
+ */
+ virtual void OnTap( const TapGesture& tap );
+
+ /**
+ * @copydoc Control::OnPan()
+ */
+ virtual void OnPan( const PanGesture& gesture );
+
+ /**
+ * @copydoc Control::OnLongPress()
+ */
+ virtual void OnLongPress( const LongPressGesture& gesture );
+
+ /**
+ * @copydoc Control::OnStageConnection()
+ */
+ virtual void OnStageConnection( int depth );
+
+ /**
+ * @copydoc Dali::CustomActorImpl::OnKeyEvent(const KeyEvent&)
+ */
+ virtual bool OnKeyEvent(const KeyEvent& event);
+
+// From ControlInterface
+
+ /**
+ * @copydoc Text::ControlInterface::AddDecoration()
+ */
+ virtual void AddDecoration( Actor& actor, bool needsClipping );
+
+ /**
+ * @copydoc Text::ControlInterface::RequestTextRelayout()
+ */
+ virtual void RequestTextRelayout();
+
+ /**
+ * @copydoc Text::ControlInterface::TextChanged()
+ */
+ virtual void TextChanged();
+
+ /**
+ * @copydoc Text::ControlInterface::MaxLengthReached()
+ */
+ virtual void MaxLengthReached();
+
+private: // Implementation
+
+ /**
+ * @copydoc Dali::Toolkit::Text::Controller::(ImfManager& imfManager, const ImfManager::ImfEventData& imfEvent)
+ */
+ ImfManager::ImfCallbackData OnImfEvent( ImfManager& imfManager, const ImfManager::ImfEventData& imfEvent );
+
+ /**
+ * @brief Callback when Clipboard signals an item should be pasted
+ * @param[in] clipboard handle to Clipboard Event Notifier
+ */
+ void OnClipboardTextSelected( ClipboardEventNotifier& clipboard );
+
+ /**
+ * @brief Get a Property Map for the image used for the required Handle Image
+ * @param[out] value the returned image property
+ * @param[in] handleType the type of handle
+ * @param[in] handleImageType the type of image for the given handleType
+ */
+ void GetHandleImagePropertyValue( Property::Value& value, Text::HandleType handleType, Text::HandleImageType handleImageType );
+
+ /**
+ * @brief Enable or disable clipping.
+ *
+ * @param[in] clipping True if clipping should be enabled.
+ * @param[in] size The area to clip within.
+ */
+ void EnableClipping( bool clipping, const Vector2& size );
+
+ /**
+ * @brief Callback when keyboard is shown/hidden.
+ *
+ * @param[in] keyboardShown True if keyboard is shown.
+ */
+ void KeyboardStatusChanged( bool keyboardShown );
+
+ /**
+ * @brief Callback when TextEditor is touched
+ *
+ * @param[in] actor TextEditor touched
+ * @param[in] event TouchEvent information
+ */
+ bool OnTouched( Actor actor, const TouchEvent& event );
+
+ /**
+ * Construct a new TextEditor.
+ */
+ TextEditor();
+
+ /**
+ * A reference counted object may only be deleted by calling Unreference()
+ */
+ virtual ~TextEditor();
+
+ // Undefined copy constructor and assignment operators
+ TextEditor(const TextEditor&);
+ TextEditor& operator=(const TextEditor& rhs);
+
+ /**
+ * @brief Render view, create and attach actor(s) to this text editor.
+ */
+ void RenderText();
+
+ // Connection needed to re-render text, when a text editor returns to the stage.
+ void OnStageConnect( Dali::Actor actor );
+
+private: // Data
+
+ // Signals
+ Toolkit::TextEditor::TextChangedSignalType mTextChangedSignal;
+
+ Text::ControllerPtr mController;
+ Text::RendererPtr mRenderer;
+ Text::DecoratorPtr mDecorator;
+ Text::ClipperPtr mClipper;
+ std::vector<Actor> mClippingDecorationActors; ///< Decoration actors which need clipping.
+
+ Actor mRenderableActor;
+
+ int mRenderingBackend;
+ bool mHasBeenStaged:1;
+};
+
+} // namespace Internal
+
+// Helpers for public-api forwarding methods
+
+inline Toolkit::Internal::TextEditor& GetImpl( Toolkit::TextEditor& textEditor )
+{
+ DALI_ASSERT_ALWAYS(textEditor);
+
+ Dali::RefObject& handle = textEditor.GetImplementation();
+
+ return static_cast<Toolkit::Internal::TextEditor&>(handle);
+}
+
+inline const Toolkit::Internal::TextEditor& GetImpl( const Toolkit::TextEditor& textEditor )
+{
+ DALI_ASSERT_ALWAYS(textEditor);
+
+ const Dali::RefObject& handle = textEditor.GetImplementation();
+
+ return static_cast<const Toolkit::Internal::TextEditor&>(handle);
+}
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_INTERNAL_TEXT_EDITOR_H__
// INTERNAL INCLUDES
#include <dali-toolkit/public-api/text/rendering-backend.h>
#include <dali-toolkit/devel-api/controls/control-depth-index-ranges.h>
-#include <dali-toolkit/internal/controls/text-controls/text-font-style.h>
#include <dali-toolkit/internal/text/rendering/text-backend.h>
+#include <dali-toolkit/internal/text/text-font-style.h>
#include <dali-toolkit/internal/text/text-view.h>
#include <dali-toolkit/internal/styling/style-manager-impl.h>
DALI_PROPERTY_REGISTRATION( Toolkit, TextField, "inputMethodSettings", MAP, INPUT_METHOD_SETTINGS )
DALI_PROPERTY_REGISTRATION( Toolkit, TextField, "inputColor", VECTOR4, INPUT_COLOR )
DALI_PROPERTY_REGISTRATION( Toolkit, TextField, "enableMarkup", BOOLEAN, ENABLE_MARKUP )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextField, "inputFontFamily", STRING, INPUT_FONT_FAMILY )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextField, "inputFontStyle", STRING, INPUT_FONT_STYLE )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextField, "inputPointSize", FLOAT, INPUT_POINT_SIZE )
DALI_SIGNAL_REGISTRATION( Toolkit, TextField, "textChanged", SIGNAL_TEXT_CHANGED )
DALI_SIGNAL_REGISTRATION( Toolkit, TextField, "maxLengthReached", SIGNAL_MAX_LENGTH_REACHED )
}
case Toolkit::TextField::Property::FONT_STYLE:
{
- SetFontStyleProperty( impl.mController, value );
+ SetFontStyleProperty( impl.mController, value, Text::FontStyle::DEFAULT );
break;
}
case Toolkit::TextField::Property::POINT_SIZE:
}
break;
}
+ case Toolkit::TextField::Property::INPUT_FONT_FAMILY:
+ {
+ if( impl.mController )
+ {
+ const std::string fontFamily = value.Get< std::string >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextField %p INPUT_FONT_FAMILY %s\n", impl.mController.Get(), fontFamily.c_str() );
+ impl.mController->SetInputFontFamily( fontFamily );
+ }
+ break;
+ }
+ case Toolkit::TextField::Property::INPUT_FONT_STYLE:
+ {
+ SetFontStyleProperty( impl.mController, value, Text::FontStyle::INPUT );
+ break;
+ }
+ case Toolkit::TextField::Property::INPUT_POINT_SIZE:
+ {
+ if( impl.mController )
+ {
+ const float pointSize = value.Get< float >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "TextField %p INPUT_POINT_SIZE %f\n", impl.mController.Get(), pointSize );
+ impl.mController->SetInputFontPointSize( pointSize );
+ }
+ break;
+ }
} // switch
} // textfield
}
}
case Toolkit::TextField::Property::FONT_STYLE:
{
- GetFontStyleProperty( impl.mController, value );
+ GetFontStyleProperty( impl.mController, value, Text::FontStyle::DEFAULT );
break;
}
case Toolkit::TextField::Property::POINT_SIZE:
}
break;
}
- case Toolkit::TextField::Property::INPUT_COLOR:
- {
- if( impl.mController )
- {
- value = impl.mController->GetInputColor();
- }
- break;
- }
case Toolkit::TextField::Property::SHADOW_OFFSET:
{
if ( impl.mController )
{
break;
}
+ case Toolkit::TextField::Property::INPUT_COLOR:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetInputColor();
+ }
+ break;
+ }
case Toolkit::TextField::Property::ENABLE_MARKUP:
{
if( impl.mController )
}
break;
}
+ case Toolkit::TextField::Property::INPUT_FONT_FAMILY:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetInputFontFamily();
+ }
+ break;
+ }
+ case Toolkit::TextField::Property::INPUT_FONT_STYLE:
+ {
+ GetFontStyleProperty( impl.mController, value, Text::FontStyle::INPUT );
+ break;
+ }
+ case Toolkit::TextField::Property::INPUT_POINT_SIZE:
+ {
+ if( impl.mController )
+ {
+ value = impl.mController->GetInputFontPointSize();
+ }
+ break;
+ }
} //switch
}
*/
virtual bool OnKeyEvent(const KeyEvent& event);
+// From ControlInterface
+
/**
* @copydoc Text::ControlInterface::AddDecoration()
*/
*/
virtual void MaxLengthReached();
+private: // Implementation
+
/**
* @copydoc Dali::Toolkit::Text::Controller::(ImfManager& imfManager, const ImfManager::ImfEventData& imfEvent)
*/
*/
void OnClipboardTextSelected( ClipboardEventNotifier& clipboard );
-private: // Implementation
-
/**
* @brief Get a Property Map for the image used for the required Handle Image
* @param[out] value the returned image property
void KeyboardStatusChanged( bool keyboardShown );
/**
- * @brief Callback when Textfield is touched
+ * @brief Callback when TextField is touched
*
* @param[in] actor TextField touched
* @param[in] event TouchEvent information
+++ /dev/null
-/*
- * Copyright (c) 2015 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.
- *
- */
-
-// FILE HEADER
-#include <dali-toolkit/internal/controls/text-controls/text-font-style.h>
-
-// INTERNAL INCLUDES
-#include <dali-toolkit/devel-api/builder/json-parser.h>
-#include <dali-toolkit/devel-api/builder/tree-node.h>
-
-namespace Dali
-{
-
-namespace Toolkit
-{
-
-namespace Text
-{
-
-namespace
-{
-const std::string STYLE_KEY( "style" );
-const std::string WIDTH_KEY( "width" );
-const std::string WEIGHT_KEY( "weight" );
-const std::string SLANT_KEY( "slant" );
-const std::string EMPTY_STRING( "" );
-
-} // namespace
-
-/**
- * @brief Creates a map with pairs 'key,value' with the font's style parameters.
- *
- * @param[in] node Data structure with the font's style parameters.
- * @param[out] map A map with the font's style parameters.
- *
- */
-void CreateFontStyleMap( const TreeNode* const node, Property::Map& map )
-{
- switch( node->GetType() )
- {
- case TreeNode::IS_NULL:
- case TreeNode::OBJECT:
- case TreeNode::ARRAY: // FALL THROUGH
- {
- break;
- }
- case TreeNode::STRING:
- {
- map.Insert( node->GetName(), Property::Value( node->GetString() ) );
- break;
- }
- case TreeNode::INTEGER:
- case TreeNode::FLOAT:
- case TreeNode::BOOLEAN: // FALL THROUGH
- {
- break;
- }
- }
-
- for( TreeNode::ConstIterator it = node->CBegin(), endIt = node->CEnd(); it != endIt; ++it )
- {
- const TreeNode::KeyNodePair& pair = *it;
- CreateFontStyleMap( &pair.second, map );
- }
-}
-
-/**
- * @brief Parses the font's style string.
- *
- * @param[in] style The font's style string.
- * @param[out] map A map with the font's style parameters.
- *
- */
-void ParseFontStyleString( const std::string& style, Property::Map& map )
-{
- Toolkit::JsonParser parser = Toolkit::JsonParser::New();
-
- if( parser.Parse( style ) )
- {
- const TreeNode* const node = parser.GetRoot();
-
- CreateFontStyleMap( node, map );
- }
-}
-
-void SetFontStyleProperty( ControllerPtr controller, const Property::Value& value )
-{
- if( controller )
- {
- const std::string style = value.Get< std::string >();
-
- // Stores the string to be recovered by the GetFontStyleProperty() function.
- controller->SetDefaultFontStyle( style );
-
- // Parses and applies the style.
- Property::Map map;
- ParseFontStyleString( style, map );
-
- if( !map.Empty() )
- {
- /// Width key
- Property::Value* widthValue = map.Find( WIDTH_KEY );
-
- if( widthValue )
- {
- const std::string widthStr = widthValue->Get<std::string>();
-
- FontWidth width = TextAbstraction::FontWidth::NORMAL;
- if( Scripting::GetEnumeration< FontWidth >( widthStr.c_str(),
- FONT_WIDTH_STRING_TABLE,
- FONT_WIDTH_STRING_TABLE_COUNT,
- width ) )
- {
- if( controller->GetDefaultFontWidth() != width )
- {
- controller->SetDefaultFontWidth( width );
- }
- }
- }
- else
- {
- controller->SetDefaultFontWidth( TextAbstraction::FontWidth::NORMAL );
- }
-
- /// Weight key
- Property::Value* weightValue = map.Find( WEIGHT_KEY );
-
- if( weightValue )
- {
- const std::string weightStr = weightValue->Get<std::string>();
-
- FontWeight weight = TextAbstraction::FontWeight::NORMAL;
- if( Scripting::GetEnumeration< FontWeight >( weightStr.c_str(),
- FONT_WEIGHT_STRING_TABLE,
- FONT_WEIGHT_STRING_TABLE_COUNT,
- weight ) )
- {
- if( controller->GetDefaultFontWeight() != weight )
- {
- controller->SetDefaultFontWeight( weight );
- }
- }
- }
- else
- {
- controller->SetDefaultFontWeight( TextAbstraction::FontWeight::NORMAL );
- }
-
- /// Slant key
- Property::Value* slantValue = map.Find( SLANT_KEY );
-
- if( slantValue )
- {
- const std::string slantStr = slantValue->Get<std::string>();
-
- FontSlant slant = TextAbstraction::FontSlant::NORMAL;
- if( Scripting::GetEnumeration< FontSlant >( slantStr.c_str(),
- FONT_SLANT_STRING_TABLE,
- FONT_SLANT_STRING_TABLE_COUNT,
- slant ) )
- {
- if( controller->GetDefaultFontSlant() != slant )
- {
- controller->SetDefaultFontSlant( slant );
- }
- }
- }
- else
- {
- controller->SetDefaultFontSlant( TextAbstraction::FontSlant::NORMAL );
- }
- }
- }
-}
-
-void GetFontStyleProperty( ControllerPtr controller, Property::Value& value )
-{
- if( controller )
- {
- value = controller->GetDefaultFontStyle();
- }
-}
-
-} // namespace Text
-
-} // namespace Toolkit
-
-} // namespace Dali
// INTERNAL INCLUDES
#include <dali-toolkit/public-api/text/rendering-backend.h>
#include <dali-toolkit/devel-api/controls/control-depth-index-ranges.h>
-#include <dali-toolkit/internal/controls/text-controls/text-font-style.h>
#include <dali-toolkit/internal/text/rendering/text-backend.h>
+#include <dali-toolkit/internal/text/text-font-style.h>
#include <dali-toolkit/internal/text/text-view.h>
#include <dali-toolkit/internal/styling/style-manager-impl.h>
}
case Toolkit::TextLabel::Property::FONT_STYLE:
{
- SetFontStyleProperty( impl.mController, value );
+ SetFontStyleProperty( impl.mController, value, Text::FontStyle::DEFAULT );
break;
}
case Toolkit::TextLabel::Property::POINT_SIZE:
}
case Toolkit::TextLabel::Property::FONT_STYLE:
{
- GetFontStyleProperty( impl.mController, value );
+ GetFontStyleProperty( impl.mController, value, Text::FontStyle::DEFAULT );
break;
}
case Toolkit::TextLabel::Property::POINT_SIZE:
void TextSelectionPopup::ShowPopup()
{
- if ( !mPopupShowing || mButtonsChanged )
+ if( ( !mPopupShowing || mButtonsChanged ) &&
+ ( Toolkit::TextSelectionPopup::NONE != mEnabledButtons ) )
{
Actor self = Self();
AddPopupOptionsToToolbar( mShowIcons, mShowCaptions );
$(toolkit_src_dir)/controls/slider/slider-impl.cpp \
$(toolkit_src_dir)/controls/super-blur-view/super-blur-view-impl.cpp \
$(toolkit_src_dir)/controls/table-view/table-view-impl.cpp \
+ $(toolkit_src_dir)/controls/text-controls/text-editor-impl.cpp \
$(toolkit_src_dir)/controls/text-controls/text-field-impl.cpp \
- $(toolkit_src_dir)/controls/text-controls/text-font-style.cpp \
$(toolkit_src_dir)/controls/text-controls/text-label-impl.cpp \
$(toolkit_src_dir)/controls/text-controls/text-selection-popup-impl.cpp \
$(toolkit_src_dir)/controls/text-controls/text-selection-toolbar-impl.cpp \
$(toolkit_src_dir)/text/logical-model-impl.cpp \
$(toolkit_src_dir)/text/markup-processor.cpp \
$(toolkit_src_dir)/text/markup-processor-color.cpp \
+ $(toolkit_src_dir)/text/markup-processor-font.cpp \
$(toolkit_src_dir)/text/markup-processor-helper-functions.cpp \
$(toolkit_src_dir)/text/multi-language-support.cpp \
$(toolkit_src_dir)/text/segmentation.cpp \
$(toolkit_src_dir)/text/text-control-interface.cpp \
$(toolkit_src_dir)/text/text-controller.cpp \
$(toolkit_src_dir)/text/text-controller-impl.cpp \
+ $(toolkit_src_dir)/text/text-font-style.cpp \
$(toolkit_src_dir)/text/text-io.cpp \
$(toolkit_src_dir)/text/text-view.cpp \
$(toolkit_src_dir)/text/text-view-interface.cpp \
: mOrientationDegrees( 0 ), // Portrait
mDefaultFontSize( -1 ),
mDefaultFontFamily(""),
- mThemeFile( DEFAULT_THEME ),
mFeedbackStyle( NULL )
{
// Add theme builder constants
// Sound & haptic style
mFeedbackStyle = new FeedbackStyle();
-
}
StyleManager::~StyleManager()
mOrientationDegrees = orientation;
// TODO: if orientation changed, apply the new style to all controls
// dont want to really do the whole load from file again if the bundle contains both portrait & landscape
- SetTheme();
+ SetTheme( mThemeFile );
}
}
}
}
-std::string StyleManager::GetDefaultFontFamily() const
+Orientation StyleManager::GetOrientation()
{
- return mDefaultFontFamily;
+ return mOrientation;
}
-Orientation StyleManager::GetOrientation()
+std::string StyleManager::GetDefaultFontFamily() const
{
- return mOrientation;
+ return mDefaultFontFamily;
}
void StyleManager::SetStyleConstant( const std::string& key, const Property::Value& value )
return false;
}
-void StyleManager::OnOrientationChanged( Orientation orientation )
+void StyleManager::RequestThemeChange( const std::string& themeFile )
{
- mOrientation = orientation;
- // TODO: if orientation changed, apply the new style to all controls
- // dont want to really do the whole load from file again if the bundle contains both portrait & landscape
- SetTheme();
+ SetTheme( themeFile );
+}
+
+void StyleManager::RequestDefaultTheme()
+{
+ std::string empty;
+ SetTheme( empty );
+}
+
+void StyleManager::ApplyThemeStyle( Toolkit::Control control )
+{
+ if( !mThemeBuilder )
+ {
+ RequestDefaultTheme();
+ }
+
+ if( mThemeBuilder )
+ {
+ ApplyStyle( mThemeBuilder, control );
+ }
+}
+
+void StyleManager::ApplyThemeStyleAtInit( Toolkit::Control control )
+{
+ ApplyThemeStyle( control );
+
+ if(mFeedbackStyle)
+ {
+ mFeedbackStyle->ObjectCreated( control );
+ }
+}
+
+void StyleManager::ApplyStyle( Toolkit::Control control, const std::string& jsonFileName, const std::string& styleName )
+{
+ bool builderReady = false;
+
+ // First look in the cache
+ Toolkit::Builder builder = FindCachedBuilder( jsonFileName );
+ if( builder )
+ {
+ builderReady = true;
+ }
+ else
+ {
+ // Merge theme and style constants
+ Property::Map constants( mThemeBuilderConstants );
+ constants.Merge( mStyleBuilderConstants );
+
+ // Create it
+ builder = CreateBuilder( constants );
+
+ if( LoadJSON( builder, jsonFileName ) )
+ {
+ CacheBuilder( builder, jsonFileName );
+ builderReady = true;
+ }
+ }
+
+ // Apply the style to the control
+ if( builderReady )
+ {
+ builder.ApplyStyle( styleName, control );
+ }
+}
+
+Toolkit::StyleManager::StyleChangeSignalType& StyleManager::StyleChangeSignal()
+{
+ return mStyleChangeSignal;
+}
+
+void StyleManager::SetTheme( const std::string& themeFile )
+{
+ bool themeLoaded = false;
+
+ mThemeBuilder = CreateBuilder( mThemeBuilderConstants );
+
+ // Always load the default theme first, then merge in the custom theme if present
+ themeLoaded = LoadJSON( mThemeBuilder, DEFAULT_THEME );
+
+ if( ! themeFile.empty() )
+ {
+ mThemeFile = themeFile;
+ themeLoaded = LoadJSON( mThemeBuilder, mThemeFile );
+ }
+
+ if( themeLoaded )
+ {
+ if(mFeedbackStyle)
+ {
+ mFeedbackStyle->StyleChanged( mThemeFile, StyleChange::THEME_CHANGE );
+ }
+
+ mStyleChangeSignal.Emit( Toolkit::StyleManager::Get(), StyleChange::THEME_CHANGE );
+ }
+ else
+ {
+ mThemeBuilder.Reset();
+ }
+}
+
+bool StyleManager::LoadFile( const std::string& filename, std::string& stringOut )
+{
+ DALI_ASSERT_DEBUG( 0 != filename.length());
+
+ // as toolkit is platform agnostic, it cannot load files from filesystem
+ // ask style monitor to load the style sheet
+ if( mStyleMonitor )
+ {
+ return mStyleMonitor.LoadThemeFile( filename, stringOut );
+ }
+
+ return false;
}
Toolkit::Builder StyleManager::CreateBuilder( const Property::Map& constants )
}
}
-void StyleManager::ApplyThemeStyle( Toolkit::Control control )
-{
- if( !mThemeBuilder )
- {
- RequestDefaultTheme();
- }
-
- if( mThemeBuilder )
- {
- ApplyStyle( mThemeBuilder, control );
- }
-}
-
-void StyleManager::ApplyThemeStyleAtInit( Toolkit::Control control )
-{
- ApplyThemeStyle( control );
-
- if(mFeedbackStyle)
- {
- mFeedbackStyle->ObjectCreated( control );
- }
-}
-
-void StyleManager::ApplyStyle( Toolkit::Control control, const std::string& jsonFileName, const std::string& styleName )
-{
- bool builderReady = false;
-
- // First look in the cache
- Toolkit::Builder builder = FindCachedBuilder( jsonFileName );
- if( builder )
- {
- builderReady = true;
- }
- else
- {
- // Merge theme and style constants
- Property::Map constants( mThemeBuilderConstants );
- constants.Merge( mStyleBuilderConstants );
-
- // Create it
- builder = CreateBuilder( constants );
-
- if( LoadJSON( builder, jsonFileName ) )
- {
- CacheBuilder( builder, jsonFileName );
- builderReady = true;
- }
- }
-
- // Apply the style to the control
- if( builderReady )
- {
- builder.ApplyStyle( styleName, control );
- }
-}
-
-bool StyleManager::LoadFile( const std::string& filename, std::string& stringOut )
-{
- DALI_ASSERT_DEBUG( 0 != filename.length());
-
- // as toolkit is platform agnostic, it cannot load files from filesystem
- // ask style monitor to load the style sheet
- if( mStyleMonitor )
- {
- return mStyleMonitor.LoadThemeFile( filename, stringOut );
- }
-
- return false;
-}
-
-Toolkit::StyleManager::StyleChangeSignalType& StyleManager::StyleChangeSignal()
-{
- return mStyleChangeSignal;
-}
-
-void StyleManager::RequestThemeChange( const std::string& themeFile )
-{
- mThemeFile = themeFile;
-
- // need to do style change synchronously as app might create a UI control on the next line
- SetTheme();
-}
-
-void StyleManager::RequestDefaultTheme()
+void StyleManager::OnOrientationChanged( Orientation orientation )
{
- RequestThemeChange( DEFAULT_THEME );
+ mOrientation = orientation;
+ // TODO: if orientation changed, apply the new style to all controls
+ // dont want to really do the whole load from file again if the bundle contains both portrait & landscape
+ SetTheme( mThemeFile );
}
-void StyleManager::SetTheme()
-{
- mThemeBuilder = CreateBuilder( mThemeBuilderConstants );
-
- if( LoadJSON( mThemeBuilder, mThemeFile ) )
- {
- if(mFeedbackStyle)
- {
- mFeedbackStyle->StyleChanged( mThemeFile, StyleChange::THEME_CHANGE );
- }
-
- mStyleChangeSignal.Emit( Toolkit::StyleManager::Get(), StyleChange::THEME_CHANGE );
- }
- else
- {
- mThemeBuilder.Reset();
- }
-}
Toolkit::Builder StyleManager::FindCachedBuilder( const std::string& key )
{
case StyleChange::THEME_CHANGE:
{
- const std::string& newTheme = styleMonitor.GetTheme();
- if( ! newTheme.empty() )
- {
- mThemeFile = newTheme;
- }
- else
- {
- mThemeFile = DEFAULT_THEME;
- }
-
- SetTheme();
+ SetTheme( styleMonitor.GetTheme() );
break;
}
}
class StyleManager : public Dali::BaseObject, public ConnectionTracker
{
public:
-
/**
* Singleton access
*
*/
StyleManager();
+protected:
+ /**
+ * @brief Destructor
+ */
+ virtual ~StyleManager();
+
+public: // Public API
+
/**
* @copydoc Toolkit::StyleManager::SetOrientationValue
*/
void RequestDefaultTheme();
/**
- * Determine if a theme change has been requested
- * @return Whether a theme request is pending
- */
- bool IsThemeRequestPending();
-
- /**
* @brief Apply the theme style to a control.
*
* @param[in] control The control to apply style.
*/
Toolkit::StyleManager::StyleChangeSignalType& StyleChangeSignal();
-protected:
-
- /**
- * @brief Destructor
- */
- virtual ~StyleManager();
-
-
-public:
+private:
+ typedef std::vector<std::string> StringList;
/**
* @brief Set the current theme. Called only once per event processing cycle.
+ * @param[in] themeFile The name of the theme file to read.
*/
- void SetTheme();
-
-private:
-
- typedef std::vector<std::string> StringList;
+ void SetTheme( const std::string& themeFile );
/**
* @brief Internal helper method to read a file from file system.
int mOrientationDegrees; ///< Directly set value of orientation
int mDefaultFontSize; ///< Logical size, not a point-size
-
std::string mDefaultFontFamily;
-
std::string mThemeFile; ///< The full path of the current theme file
Property::Map mThemeBuilderConstants; ///< Contants to give the theme builder
} // namespace Dali
#endif // __DALI_TOOLKIT_INTERNAL_STYLE_MANAGER_H__
-
const ScriptRun& scriptRun = *it;
const CharacterIndex lastScriptRunIndex = scriptRun.characterRun.characterIndex + scriptRun.characterRun.numberOfCharacters;
- if( TextAbstraction::IsRightToLeftScript( scriptRun.script ) && // The script is right to left.
- ( lastScriptRunIndex > paragraphCharacterIndex ) ) // It isn't part of a previous paragraph.
+ if( ( lastScriptRunIndex > paragraphCharacterIndex ) && // It isn't part of a previous paragraph.
+ TextAbstraction::IsRightToLeftScript( scriptRun.script ) ) // The script is right to left.
{
// Find the paragraphs which contains this script run.
// Consider:
}
bool GetMirroredText( const Vector<Character>& text,
- Vector<Character>& mirroredText,
- const Vector<BidirectionalParagraphInfoRun>& bidirectionalInfo )
+ const Vector<CharacterDirection>& directions,
+ const Vector<BidirectionalParagraphInfoRun>& bidirectionalInfo,
+ Vector<Character>& mirroredText )
{
bool hasTextMirrored = false;
mirroredText = text;
Character* mirroredTextBuffer = mirroredText.Begin();
+ CharacterDirection* directionsBuffer = directions.Begin();
// Traverse the paragraphs and mirror the right to left ones.
for( Vector<BidirectionalParagraphInfoRun>::ConstIterator it = bidirectionalInfo.Begin(),
it != endIt;
++it )
{
- const BidirectionalParagraphInfoRun& run = *it;
+ const BidirectionalParagraphInfoRun& paragraph = *it;
- const bool tmpMirrored = bidirectionalSupport.GetMirroredText( mirroredTextBuffer + run.characterRun.characterIndex,
- run.characterRun.numberOfCharacters );
+ const bool tmpMirrored = bidirectionalSupport.GetMirroredText( mirroredTextBuffer + paragraph.characterRun.characterIndex,
+ directionsBuffer + paragraph.characterRun.characterIndex,
+ paragraph.characterRun.numberOfCharacters );
hasTextMirrored = hasTextMirrored || tmpMirrored;
}
* @brief Replaces any character in the right to left paragraphs which could be mirrored.
*
* @param[in] text The text.
- * @param[in] mirroredText The mirroredText.
+ * @param[in] directions Vector with the direction of each paragraph.
* @param[in] bidirectionalInfo Vector with the bidirectional infor for each paragraph.
+ * @param[out] mirroredText The mirroredText.
*
* @return @e true if a character has been replaced.
*/
bool GetMirroredText( const Vector<Character>& text,
- Vector<Character>& mirroredText,
- const Vector<BidirectionalParagraphInfoRun>& bidirectionalInfo );
+ const Vector<CharacterDirection>& directions,
+ const Vector<BidirectionalParagraphInfoRun>& bidirectionalInfo,
+ Vector<Character>& mirroredText );
/**
* @brief Retrieves the character's directions.
U0, U0, U0, U0, // Non valid.
U0, U0, U0, U0, // Non valid.
};
+
+ const uint8_t CR = 0xd;
+ const uint8_t LF = 0xa;
} // namespace
uint8_t GetUtf8Length( uint8_t utf8LeadByte )
{
case U1:
{
- *utf32++ = leadByte;
- begin++;
+ if( CR == leadByte )
+ {
+ // Replace CR+LF or CR by LF
+ *utf32++ = LF;
+
+ // Look ahead if the next one is a LF.
+ ++begin;
+ if( begin < end )
+ {
+ if( LF == *begin )
+ {
+ ++begin;
+ }
+ }
+ }
+ else
+ {
+ *utf32++ = leadByte;
+ begin++;
+ }
break;
}
*
* The @p utf32 buffer needs to be big enough to store all the characters.
*
+ * If the text contains a single 'CR' character or a pair 'CR'+'LF', they are replaced by a 'LF'.
+ *
+ * @note GetNumberOfUtf8Characters() does not convert 'CR' or 'CR'+'LF' to 'LF' so the return number
+ * of characters of that method may be higher than the number of characters returned by this one.
+ *
* @param[in] utf8 The pointer to the UTF8 array.
* @param[in] length The length of the UTF8 array.
* @param[out] utf32 The pointer to the UTF32 array.
HandleImpl& grabHandle = mHandle[GRAB_HANDLE];
if( !grabHandle.actor )
{
- grabHandle.actor = ImageView::New( mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED] );
- GetImpl( grabHandle.actor).SetDepthIndex( DepthIndex::DECORATION );
- grabHandle.actor.SetAnchorPoint( AnchorPoint::TOP_CENTER );
- // Area that Grab handle responds to, larger than actual handle so easier to move
-#ifdef DECORATOR_DEBUG
- grabHandle.actor.SetName( "GrabHandleActor" );
- if ( Dali::Internal::gLogFilter->IsEnabledFor( Debug::Verbose ) )
- {
- grabHandle.grabArea = Control::New();
- Toolkit::Control control = Toolkit::Control::DownCast( grabHandle.grabArea );
- control.SetBackgroundColor( Vector4( 1.0f, 1.0f, 1.0f, 0.5f ) );
- grabHandle.grabArea.SetName( "GrabArea" );
- }
- else
+ if( mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED] )
{
- grabHandle.grabArea = Actor::New();
- grabHandle.grabArea.SetName( "GrabArea" );
- }
+ grabHandle.actor = ImageView::New( mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED] );
+ GetImpl( grabHandle.actor).SetDepthIndex( DepthIndex::DECORATION );
+ grabHandle.actor.SetAnchorPoint( AnchorPoint::TOP_CENTER );
+
+ // Area that Grab handle responds to, larger than actual handle so easier to move
+#ifdef DECORATOR_DEBUG
+ grabHandle.actor.SetName( "GrabHandleActor" );
+ if ( Dali::Internal::gLogFilter->IsEnabledFor( Debug::Verbose ) )
+ {
+ grabHandle.grabArea = Control::New();
+ Toolkit::Control control = Toolkit::Control::DownCast( grabHandle.grabArea );
+ control.SetBackgroundColor( Vector4( 1.0f, 1.0f, 1.0f, 0.5f ) );
+ grabHandle.grabArea.SetName( "GrabArea" );
+ }
+ else
+ {
+ grabHandle.grabArea = Actor::New();
+ grabHandle.grabArea.SetName( "GrabArea" );
+ }
#else
- grabHandle.grabArea = Actor::New();
+ grabHandle.grabArea = Actor::New();
#endif
- grabHandle.grabArea.SetParentOrigin( ParentOrigin::TOP_CENTER );
- grabHandle.grabArea.SetAnchorPoint( AnchorPoint::TOP_CENTER );
- grabHandle.grabArea.SetResizePolicy( ResizePolicy::SIZE_RELATIVE_TO_PARENT, Dimension::ALL_DIMENSIONS );
- grabHandle.grabArea.SetSizeModeFactor( DEFAULT_GRAB_HANDLE_RELATIVE_SIZE );
- grabHandle.actor.Add( grabHandle.grabArea );
- grabHandle.actor.SetColor( mHandleColor );
+ grabHandle.grabArea.SetParentOrigin( ParentOrigin::TOP_CENTER );
+ grabHandle.grabArea.SetAnchorPoint( AnchorPoint::TOP_CENTER );
+ grabHandle.grabArea.SetResizePolicy( ResizePolicy::SIZE_RELATIVE_TO_PARENT, Dimension::ALL_DIMENSIONS );
+ grabHandle.grabArea.SetSizeModeFactor( DEFAULT_GRAB_HANDLE_RELATIVE_SIZE );
+ grabHandle.actor.Add( grabHandle.grabArea );
+ grabHandle.actor.SetColor( mHandleColor );
- grabHandle.grabArea.TouchedSignal().Connect( this, &Decorator::Impl::OnGrabHandleTouched );
- mTapDetector.Attach( grabHandle.grabArea );
- mPanGestureDetector.Attach( grabHandle.grabArea );
+ grabHandle.grabArea.TouchedSignal().Connect( this, &Decorator::Impl::OnGrabHandleTouched );
+ mTapDetector.Attach( grabHandle.grabArea );
+ mPanGestureDetector.Attach( grabHandle.grabArea );
- mActiveLayer.Add( grabHandle.actor );
+ mActiveLayer.Add( grabHandle.actor );
+ }
}
- if( !grabHandle.actor.GetParent() )
+ if( grabHandle.actor && !grabHandle.actor.GetParent() )
{
mActiveLayer.Add( grabHandle.actor );
}
HandleImpl& primary = mHandle[ LEFT_SELECTION_HANDLE ];
if( !primary.actor )
{
- primary.actor = ImageView::New( mHandleImages[LEFT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED] );
+ if( mHandleImages[LEFT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED] )
+ {
+ primary.actor = ImageView::New( mHandleImages[LEFT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED] );
#ifdef DECORATOR_DEBUG
- primary.actor.SetName("SelectionHandleOne");
+ primary.actor.SetName("SelectionHandleOne");
#endif
- primary.actor.SetAnchorPoint( AnchorPoint::TOP_RIGHT ); // Change to BOTTOM_RIGHT if Look'n'Feel requires handle above text.
- GetImpl( primary.actor ).SetDepthIndex( DepthIndex::DECORATION );
- primary.actor.SetColor( mHandleColor );
+ primary.actor.SetAnchorPoint( AnchorPoint::TOP_RIGHT ); // Change to BOTTOM_RIGHT if Look'n'Feel requires handle above text.
+ GetImpl( primary.actor ).SetDepthIndex( DepthIndex::DECORATION );
+ primary.actor.SetColor( mHandleColor );
- primary.grabArea = Actor::New(); // Area that Grab handle responds to, larger than actual handle so easier to move
+ primary.grabArea = Actor::New(); // Area that Grab handle responds to, larger than actual handle so easier to move
#ifdef DECORATOR_DEBUG
- primary.grabArea.SetName("SelectionHandleOneGrabArea");
+ primary.grabArea.SetName("SelectionHandleOneGrabArea");
#endif
- primary.grabArea.SetResizePolicy( ResizePolicy::SIZE_RELATIVE_TO_PARENT, Dimension::ALL_DIMENSIONS );
- primary.grabArea.SetParentOrigin( ParentOrigin::TOP_CENTER );
- primary.grabArea.SetAnchorPoint( AnchorPoint::TOP_CENTER );
- primary.grabArea.SetSizeModeFactor( DEFAULT_SELECTION_HANDLE_RELATIVE_SIZE );
+ primary.grabArea.SetResizePolicy( ResizePolicy::SIZE_RELATIVE_TO_PARENT, Dimension::ALL_DIMENSIONS );
+ primary.grabArea.SetParentOrigin( ParentOrigin::TOP_CENTER );
+ primary.grabArea.SetAnchorPoint( AnchorPoint::TOP_CENTER );
+ primary.grabArea.SetSizeModeFactor( DEFAULT_SELECTION_HANDLE_RELATIVE_SIZE );
- mTapDetector.Attach( primary.grabArea );
- mPanGestureDetector.Attach( primary.grabArea );
- primary.grabArea.TouchedSignal().Connect( this, &Decorator::Impl::OnHandleOneTouched );
+ mTapDetector.Attach( primary.grabArea );
+ mPanGestureDetector.Attach( primary.grabArea );
+ primary.grabArea.TouchedSignal().Connect( this, &Decorator::Impl::OnHandleOneTouched );
- primary.actor.Add( primary.grabArea );
+ primary.actor.Add( primary.grabArea );
- CreateHandleMarker( primary, mHandleImages[LEFT_SELECTION_HANDLE_MARKER][HANDLE_IMAGE_RELEASED], LEFT_SELECTION_HANDLE );
+ CreateHandleMarker( primary, mHandleImages[LEFT_SELECTION_HANDLE_MARKER][HANDLE_IMAGE_RELEASED], LEFT_SELECTION_HANDLE );
+ }
}
- if( !primary.actor.GetParent() )
+ if( primary.actor && !primary.actor.GetParent() )
{
mActiveLayer.Add( primary.actor );
}
HandleImpl& secondary = mHandle[ RIGHT_SELECTION_HANDLE ];
if( !secondary.actor )
{
- secondary.actor = ImageView::New( mHandleImages[RIGHT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED] );
+ if( mHandleImages[RIGHT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED] )
+ {
+ secondary.actor = ImageView::New( mHandleImages[RIGHT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED] );
#ifdef DECORATOR_DEBUG
- secondary.actor.SetName("SelectionHandleTwo");
+ secondary.actor.SetName("SelectionHandleTwo");
#endif
- secondary.actor.SetAnchorPoint( AnchorPoint::TOP_LEFT ); // Change to BOTTOM_LEFT if Look'n'Feel requires handle above text.
- GetImpl( secondary.actor ).SetDepthIndex( DepthIndex::DECORATION );
- secondary.actor.SetColor( mHandleColor );
+ secondary.actor.SetAnchorPoint( AnchorPoint::TOP_LEFT ); // Change to BOTTOM_LEFT if Look'n'Feel requires handle above text.
+ GetImpl( secondary.actor ).SetDepthIndex( DepthIndex::DECORATION );
+ secondary.actor.SetColor( mHandleColor );
- secondary.grabArea = Actor::New(); // Area that Grab handle responds to, larger than actual handle so easier to move
+ secondary.grabArea = Actor::New(); // Area that Grab handle responds to, larger than actual handle so easier to move
#ifdef DECORATOR_DEBUG
- secondary.grabArea.SetName("SelectionHandleTwoGrabArea");
+ secondary.grabArea.SetName("SelectionHandleTwoGrabArea");
#endif
- secondary.grabArea.SetResizePolicy( ResizePolicy::SIZE_RELATIVE_TO_PARENT, Dimension::ALL_DIMENSIONS );
- secondary.grabArea.SetParentOrigin( ParentOrigin::TOP_CENTER );
- secondary.grabArea.SetAnchorPoint( AnchorPoint::TOP_CENTER );
- secondary.grabArea.SetSizeModeFactor( DEFAULT_SELECTION_HANDLE_RELATIVE_SIZE );
+ secondary.grabArea.SetResizePolicy( ResizePolicy::SIZE_RELATIVE_TO_PARENT, Dimension::ALL_DIMENSIONS );
+ secondary.grabArea.SetParentOrigin( ParentOrigin::TOP_CENTER );
+ secondary.grabArea.SetAnchorPoint( AnchorPoint::TOP_CENTER );
+ secondary.grabArea.SetSizeModeFactor( DEFAULT_SELECTION_HANDLE_RELATIVE_SIZE );
- mTapDetector.Attach( secondary.grabArea );
- mPanGestureDetector.Attach( secondary.grabArea );
- secondary.grabArea.TouchedSignal().Connect( this, &Decorator::Impl::OnHandleTwoTouched );
+ mTapDetector.Attach( secondary.grabArea );
+ mPanGestureDetector.Attach( secondary.grabArea );
+ secondary.grabArea.TouchedSignal().Connect( this, &Decorator::Impl::OnHandleTwoTouched );
- secondary.actor.Add( secondary.grabArea );
+ secondary.actor.Add( secondary.grabArea );
- CreateHandleMarker( secondary, mHandleImages[RIGHT_SELECTION_HANDLE_MARKER][HANDLE_IMAGE_RELEASED], RIGHT_SELECTION_HANDLE );
+ CreateHandleMarker( secondary, mHandleImages[RIGHT_SELECTION_HANDLE_MARKER][HANDLE_IMAGE_RELEASED], RIGHT_SELECTION_HANDLE );
+ }
}
- if( !secondary.actor.GetParent() )
+ if( secondary.actor && !secondary.actor.GetParent() )
{
mActiveLayer.Add( secondary.actor );
}
// The SetGrabHandleImage() method will change the orientation.
const float yLocalPosition = grabHandle.verticallyFlipped ? grabHandle.position.y : grabHandle.position.y + grabHandle.lineHeight;
- grabHandle.actor.SetPosition( grabHandle.position.x + floor( 0.5f * mCursorWidth ),
- yLocalPosition ); // TODO : Fix for multiline.
+ if( grabHandle.actor )
+ {
+ grabHandle.actor.SetPosition( grabHandle.position.x + floor( 0.5f * mCursorWidth ),
+ yLocalPosition ); // TODO : Fix for multiline.
+ }
}
void SetSelectionHandlePosition( HandleType type )
if( flipHandle )
{
- if( !handle.horizontallyFlipped )
+ if( handle.actor && !handle.horizontallyFlipped )
{
// Change the anchor point to flip the image.
handle.actor.SetAnchorPoint( isPrimaryHandle ? AnchorPoint::TOP_LEFT : AnchorPoint::TOP_RIGHT );
}
else
{
- if( handle.horizontallyFlipped )
+ if( handle.actor && handle.horizontallyFlipped )
{
// Reset the anchor point.
handle.actor.SetAnchorPoint( isPrimaryHandle ? AnchorPoint::TOP_RIGHT : AnchorPoint::TOP_LEFT );
// The SetHandleImage() method will change the orientation.
const float yLocalPosition = handle.verticallyFlipped ? handle.position.y : handle.position.y + handle.lineHeight;
- handle.actor.SetPosition( handle.position.x,
- yLocalPosition ); // TODO : Fix for multiline.
+ if( handle.actor )
+ {
+ handle.actor.SetPosition( handle.position.x,
+ yLocalPosition ); // TODO : Fix for multiline.
+ }
}
void SetHandleImage( HandleType type )
if( mHighlightRenderer )
{
- mHighlightRenderer.SetDepthIndex( mTextDepth - 2u ); // text is rendered at mTextDepth and text's shadow at mTextDepth -1u.
+ mHighlightRenderer.SetProperty( Renderer::Property::DEPTH_INDEX, mTextDepth - 2 ); // text is rendered at mTextDepth and text's shadow at mTextDepth -1u.
}
}
}
mController.DecorationEvent( type, HANDLE_RELEASED, x, y );
}
- handle.actor.SetImage( mHandleImages[type][HANDLE_IMAGE_RELEASED] );
+ if( handle.actor )
+ {
+ handle.actor.SetImage( mHandleImages[type][HANDLE_IMAGE_RELEASED] );
+ }
handle.pressed = false;
mHandlePanning = false;
--- /dev/null
+#ifndef __DALI_TOOLKIT_TEXT_FONT_DESCRIPTION_RUN_H__
+#define __DALI_TOOLKIT_TEXT_FONT_DESCRIPTION_RUN_H__
+
+/*
+ * Copyright (c) 2016 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 INCLUDES
+#include <dali/devel-api/text-abstraction/font-list.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/character-run.h>
+#include <dali-toolkit/internal/text/text-definitions.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+/**
+ * @brief Run of characters with the same font.
+ */
+struct FontDescriptionRun
+{
+ CharacterRun characterRun; ///< The initial character index and the number of characters of the run.
+ char* familyName; ///< The font's family name.
+ Length familyLength; ///< The length of the font's family name.
+ FontWeight weight; ///< The font's weight.
+ FontWidth width; ///< The font's width.
+ FontSlant slant; ///< The font's slant.
+ PointSize26Dot6 size; ///< The font's size.
+
+ bool familyDefined : 1; ///< Whether the font's family is defined.
+ bool weightDefined : 1; ///< Whether the font's weight is defined.
+ bool widthDefined : 1; ///< Whether the font's width is defined.
+ bool slantDefined : 1; ///< Whether the font's slant is defined.
+ bool sizeDefined : 1; ///< Whether the font's size is defined.
+};
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_TEXT_FONT_DESCRIPTION_RUN_H__
{
CharacterRun characterRun; ///< The initial character index and the number of characters of the run.
FontId fontId; ///< Font id of the run.
- bool isDefault; ///< Whether the font is a default font not defined by the user.
};
} // namespace Text
// EXTERNAL INCLUDES
#include <dali/public-api/math/vector4.h>
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/text-definitions.h>
+
namespace Dali
{
*/
struct InputStyle
{
-Vector4 textColor;
+ InputStyle()
+ : textColor( Color::BLACK ),
+ fontStyle(),
+ familyName(),
+ weight( TextAbstraction::FontWeight::NORMAL ),
+ width( TextAbstraction::FontWidth::NORMAL ),
+ slant( TextAbstraction::FontSlant::NORMAL ),
+ size( 0.f ),
+ familyDefined( false ),
+ weightDefined( false ),
+ widthDefined( false ),
+ slantDefined( false ),
+ sizeDefined( false )
+ {}
+
+ ~InputStyle()
+ {};
+
+ Vector4 textColor; ///< The text's color.
+ std::string fontStyle; ///< The font's style string.
+ std::string familyName; ///< The font's family name.
+ FontWeight weight; ///< The font's weight.
+ FontWidth width; ///< The font's width.
+ FontSlant slant; ///< The font's slant.
+ float size; ///< The font's size.
+
+ bool familyDefined : 1; ///< Whether the font's family is defined.
+ bool weightDefined : 1; ///< Whether the font's weight is defined.
+ bool widthDefined : 1; ///< Whether the font's width is defined.
+ bool slantDefined : 1; ///< Whether the font's slant is defined.
+ bool sizeDefined : 1; ///< Whether the font's size is defined.
};
} // namespace Text
namespace Text
{
+void FreeFontFamilyNames( Vector<FontDescriptionRun>& fontDescriptionRuns )
+{
+ for( Vector<FontDescriptionRun>::Iterator it = fontDescriptionRuns.Begin(),
+ endIt = fontDescriptionRuns.End();
+ it != endIt;
+ ++it )
+ {
+ delete (*it).familyName;
+ }
+
+ fontDescriptionRuns.Clear();
+}
+
LogicalModelPtr LogicalModel::New()
{
return LogicalModelPtr( new LogicalModel() );
totalNumberOfCharacters,
mColorRuns,
removedColorRuns );
+
+ // Process the font description runs.
+ Vector<FontDescriptionRun> removedFontDescriptionRuns;
+ UpdateCharacterRuns<FontDescriptionRun>( index,
+ numberOfCharacters,
+ totalNumberOfCharacters,
+ mFontDescriptionRuns,
+ removedFontDescriptionRuns );
+
+ // Free memory allocated for the font family name.
+ FreeFontFamilyNames( removedFontDescriptionRuns );
}
void LogicalModel::RetrieveStyle( CharacterIndex index, InputStyle& style )
{
unsigned int runIndex = 0u;
- unsigned int lastRunIndex = 0u;
- bool overriden = false;
// Set the text color.
- for( Vector<ColorRun>::ConstIterator it = mColorRuns.Begin(),
+ bool colorOverriden = false;
+ unsigned int colorIndex = 0u;
+ const ColorRun* const colorRunsBuffer = mColorRuns.Begin();
+ for( Vector<ColorRun>::ConstIterator it = colorRunsBuffer,
endIt = mColorRuns.End();
it != endIt;
++it, ++runIndex )
if( ( colorRun.characterRun.characterIndex <= index ) &&
( index < colorRun.characterRun.characterIndex + colorRun.characterRun.numberOfCharacters ) )
{
- lastRunIndex = runIndex;
- overriden = true;
+ colorIndex = runIndex;
+ colorOverriden = true;
}
}
// Set the text's color if it's overriden.
- if( overriden )
+ if( colorOverriden )
{
- style.textColor = ( *( mColorRuns.Begin() + lastRunIndex ) ).color;
+ style.textColor = ( *( colorRunsBuffer + colorIndex ) ).color;
}
+
+ // Reset the run index.
+ runIndex = 0u;
+
+ // Set the font's parameters.
+ bool nameOverriden = false;
+ bool weightOverriden = false;
+ bool widthOverriden = false;
+ bool slantOverriden = false;
+ bool sizeOverriden = false;
+ unsigned int nameIndex = 0u;
+ unsigned int weightIndex = 0u;
+ unsigned int widthIndex = 0u;
+ unsigned int slantIndex = 0u;
+ unsigned int sizeIndex = 0u;
+ const FontDescriptionRun* const fontDescriptionRunsBuffer = mFontDescriptionRuns.Begin();
+ for( Vector<FontDescriptionRun>::ConstIterator it = fontDescriptionRunsBuffer,
+ endIt = mFontDescriptionRuns.End();
+ it != endIt;
+ ++it, ++runIndex )
+ {
+ const FontDescriptionRun& fontDescriptionRun = *it;
+
+ if( ( fontDescriptionRun.characterRun.characterIndex <= index ) &&
+ ( index < fontDescriptionRun.characterRun.characterIndex + fontDescriptionRun.characterRun.numberOfCharacters ) )
+ {
+ if( fontDescriptionRun.familyDefined )
+ {
+ nameIndex = runIndex;
+ nameOverriden = true;
+ }
+
+ if( fontDescriptionRun.weightDefined )
+ {
+ weightIndex = runIndex;
+ weightOverriden = true;
+ }
+
+ if( fontDescriptionRun.widthDefined )
+ {
+ widthIndex = runIndex;
+ widthOverriden = true;
+ }
+
+ if( fontDescriptionRun.slantDefined )
+ {
+ slantIndex = runIndex;
+ slantOverriden = true;
+ }
+
+ if( fontDescriptionRun.sizeDefined )
+ {
+ sizeIndex = runIndex;
+ sizeOverriden = true;
+ }
+ }
+ }
+
+ // Set the font's family name if it's overriden.
+ if( nameOverriden )
+ {
+ const FontDescriptionRun& fontDescriptionRun = *( fontDescriptionRunsBuffer + nameIndex );
+
+ style.familyName = std::string( fontDescriptionRun.familyName, fontDescriptionRun.familyLength );
+ style.familyDefined = true;
+ }
+
+ // Set the font's weight if it's overriden.
+ if( weightOverriden )
+ {
+ const FontDescriptionRun& fontDescriptionRun = *( fontDescriptionRunsBuffer + weightIndex );
+
+ style.weight = fontDescriptionRun.weight;
+ style.weightDefined = true;
+ }
+
+ // Set the font's width if it's overriden.
+ if( widthOverriden )
+ {
+ const FontDescriptionRun& fontDescriptionRun = *( fontDescriptionRunsBuffer + widthIndex );
+
+ style.width = fontDescriptionRun.width;
+ style.widthDefined = true;
+ }
+
+ // Set the font's slant if it's overriden.
+ if( slantOverriden )
+ {
+ const FontDescriptionRun& fontDescriptionRun = *( fontDescriptionRunsBuffer + slantIndex );
+
+ style.slant = fontDescriptionRun.slant;
+ style.slantDefined = true;
+ }
+
+ // Set the font's size if it's overriden.
+ if( sizeOverriden )
+ {
+ const FontDescriptionRun& fontDescriptionRun = *( fontDescriptionRunsBuffer + sizeIndex );
+
+ style.size = static_cast<float>( fontDescriptionRun.size ) / 64.f;
+ style.sizeDefined = true;
+ }
+
+ // Reset the run index.
+ runIndex = 0u;
+}
+
+void LogicalModel::ClearFontDescriptionRuns()
+{
+ FreeFontFamilyNames( mFontDescriptionRuns );
}
LogicalModel::~LogicalModel()
{
+ ClearFontDescriptionRuns();
}
LogicalModel::LogicalModel()
#include <dali-toolkit/internal/text/bidirectional-paragraph-info-run.h>
#include <dali-toolkit/internal/text/color-run.h>
#include <dali-toolkit/internal/text/font-run.h>
+#include <dali-toolkit/internal/text/font-description-run.h>
#include <dali-toolkit/internal/text/script-run.h>
namespace Dali
*/
void RetrieveStyle( CharacterIndex index, InputStyle& style );
+ /**
+ * @brief Clears the font description runs.
+ */
+ void ClearFontDescriptionRuns();
+
protected:
/**
Vector<ScriptRun> mScriptRuns;
Vector<FontRun> mFontRuns;
Vector<ColorRun> mColorRuns;
+ Vector<FontDescriptionRun> mFontDescriptionRuns;
Vector<LineBreakInfo> mLineBreakInfo;
Vector<WordBreakInfo> mWordBreakInfo;
Vector<BidirectionalParagraphInfoRun> mBidirectionalParagraphInfo;
--- /dev/null
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+// FILE HEADER
+#include <dali-toolkit/internal/text/markup-processor-font.h>
+
+// EXTERNAL INCLUDES
+#include <dali/public-api/common/dali-vector.h>
+#include <memory.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/font-description-run.h>
+#include <dali-toolkit/internal/text/markup-processor-helper-functions.h>
+#include <dali-toolkit/internal/text/text-font-style.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+namespace
+{
+const std::string XHTML_FAMILY_ATTRIBUTE("family");
+const std::string XHTML_SIZE_ATTRIBUTE("size");
+const std::string XHTML_WEIGHT_ATTRIBUTE("weight");
+const std::string XHTML_WIDTH_ATTRIBUTE("width");
+const std::string XHTML_SLANT_ATTRIBUTE("slant");
+
+const unsigned int MAX_FONT_ATTRIBUTE_SIZE = 15u; ///< The maximum length of any of the possible 'weight', 'width' or 'slant' values.
+}
+
+void ProcessFontTag( const Tag& tag, FontDescriptionRun& fontRun )
+{
+ for( Vector<Attribute>::ConstIterator it = tag.attributes.Begin(),
+ endIt = tag.attributes.End();
+ it != endIt;
+ ++it )
+ {
+ const Attribute& attribute( *it );
+ if( TokenComparison( XHTML_FAMILY_ATTRIBUTE, attribute.nameBuffer, attribute.nameLength ) )
+ {
+ fontRun.familyDefined = true;
+ fontRun.familyLength = attribute.valueLength;
+ fontRun.familyName = new char[fontRun.familyLength];
+ memcpy( fontRun.familyName, attribute.valueBuffer, fontRun.familyLength );
+ // The memory is freed when the font run is removed from the logical model.
+ }
+ else if( TokenComparison( XHTML_SIZE_ATTRIBUTE, attribute.nameBuffer, attribute.nameLength ) )
+ {
+ // 64.f is used to convert from point size to 26.6 pixel format.
+ fontRun.size = static_cast<PointSize26Dot6>( StringToFloat( attribute.valueBuffer ) * 64.f );
+ fontRun.sizeDefined = true;
+ }
+ else if( TokenComparison( XHTML_WEIGHT_ATTRIBUTE, attribute.nameBuffer, attribute.nameLength ) )
+ {
+ // The StringToWeight() uses the Scripting::GetEnumeration() function which requires the input string to end with a '\0' char.
+ char value[MAX_FONT_ATTRIBUTE_SIZE+1u];
+ const Length length = attribute.valueLength > MAX_FONT_ATTRIBUTE_SIZE ? MAX_FONT_ATTRIBUTE_SIZE : attribute.valueLength;
+ memcpy( value, attribute.valueBuffer, length );
+ value[length] = 0;
+
+ fontRun.weight = StringToWeight( value );
+ fontRun.weightDefined = true;
+ }
+ else if( TokenComparison( XHTML_WIDTH_ATTRIBUTE, attribute.nameBuffer, attribute.nameLength ) )
+ {
+ // The StringToWidth() uses the Scripting::GetEnumeration() function which requires the input string to end with a '\0' char.
+ char value[MAX_FONT_ATTRIBUTE_SIZE+1u];
+ const Length length = attribute.valueLength > MAX_FONT_ATTRIBUTE_SIZE ? MAX_FONT_ATTRIBUTE_SIZE : attribute.valueLength;
+ memcpy( value, attribute.valueBuffer, length );
+ value[length] = 0;
+
+ fontRun.width = StringToWidth( value );
+ fontRun.widthDefined = true;
+ }
+ else if( TokenComparison( XHTML_SLANT_ATTRIBUTE, attribute.nameBuffer, attribute.nameLength ) )
+ {
+ // The StringToSlant() uses the Scripting::GetEnumeration() function which requires the input string to end with a '\0' char.
+ char value[MAX_FONT_ATTRIBUTE_SIZE+1u];
+ const Length length = attribute.valueLength > MAX_FONT_ATTRIBUTE_SIZE ? MAX_FONT_ATTRIBUTE_SIZE : attribute.valueLength;
+ memcpy( value, attribute.valueBuffer, length );
+ value[length] = 0;
+
+ fontRun.slant = StringToSlant( value );
+ fontRun.slantDefined = true;
+ }
+ }
+}
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_TOOLKIT_TEXT_MARKUP_PROCESSOR_FONT_H__
+#define __DALI_TOOLKIT_TEXT_MARKUP_PROCESSOR_FONT_H__
+
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+struct Tag;
+struct FontDescriptionRun;
+
+/**
+ * @brief Retrieves the font attributes from the tag and sets it to the font run.
+ *
+ * @param[in] tag The font tag and its attributes.
+ * @param[in,out] fontRun The font description run.
+ */
+void ProcessFontTag( const Tag& tag, FontDescriptionRun& fontRun );
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_TEXT_MARKUP_PROCESSOR_FONT_H__
return static_cast<unsigned int>( strtoul( uintStr, NULL, 16 ) );
}
+float StringToFloat( const char* const floatStr )
+{
+ return static_cast<float>( strtod( floatStr, NULL ) );
+}
+
void UintColorToVector4( unsigned int color, Vector4& retColor )
{
retColor.a = static_cast<float>( ( color & 0xFF000000 ) >> 24u ) / 255.f;
unsigned int StringToHex( const char* const uintStr );
/**
+ * @brief Converts a string into a float value.
+ *
+ * @param[in] floatStr A float packed inside a string.
+ *
+ * @return The float value.
+ */
+float StringToFloat( const char* const floatStr );
+
+/**
* @brief Converts an ARGB color packed in 4 byte unsigned int into a Vector4 color used in Dali.
*
* @param[in] color An ARGB color packed in an unsigned int.
// INTERNAL INCLUDES
#include <dali-toolkit/internal/text/character-set-conversion.h>
#include <dali-toolkit/internal/text/markup-processor-color.h>
+#include <dali-toolkit/internal/text/markup-processor-font.h>
#include <dali-toolkit/internal/text/markup-processor-helper-functions.h>
namespace Dali
const std::string XHTML_GLOW_TAG("glow");
const std::string XHTML_OUTLINE_TAG("outline");
-const char LESS_THAN = '<';
-const char GREATER_THAN = '>';
-const char EQUAL = '=';
-const char QUOTATION_MARK = '\'';
-const char LINE_SEPARATOR_CR = 0x0D; // Carriage return character CR
-const char LINE_SEPARATOR_LF = 0x0A; // New line character LF
-const char SLASH = '/';
-const char BACK_SLASH = '\\';
+const char LESS_THAN = '<';
+const char GREATER_THAN = '>';
+const char EQUAL = '=';
+const char QUOTATION_MARK = '\'';
+const char SLASH = '/';
+const char BACK_SLASH = '\\';
-const char WHITE_SPACE = 0x20; // ASCII value of the white space.
+const char WHITE_SPACE = 0x20; // ASCII value of the white space.
const unsigned int MAX_NUM_OF_ATTRIBUTES = 5u; ///< The font tag has the 'family', 'size' 'weight', 'width' and 'slant' attrubutes.
-
const unsigned int DEFAULT_VECTOR_SIZE = 16u; ///< Default size of run vectors.
/**
// Points the next free position in the vector of runs.
StyleStack::RunIndex colorRunIndex = 0u;
+ StyleStack::RunIndex fontRunIndex = 0u;
// Give an initial default value to the model's vectors.
markupProcessData.colorRuns.Reserve( DEFAULT_VECTOR_SIZE );
+ markupProcessData.fontRuns.Reserve( DEFAULT_VECTOR_SIZE );
// Get the mark-up string buffer.
const char* markupStringBuffer = markupString.c_str();
if( !tag.isEndTag )
{
// Create a new font run.
+ FontDescriptionRun fontRun;
+ fontRun.characterRun.numberOfCharacters = 0u;
+
+ // Fill the run with the parameters.
+ fontRun.characterRun.characterIndex = characterIndex;
+ fontRun.slant = TextAbstraction::FontSlant::ITALIC;
+
+ fontRun.familyName = NULL;
+ fontRun.familyDefined = false;
+ fontRun.weightDefined = false;
+ fontRun.widthDefined = false;
+ fontRun.slantDefined = true;
+ fontRun.sizeDefined = false;
+
+ // Push the font run in the logical model.
+ markupProcessData.fontRuns.PushBack( fontRun );
+
+ // Push the index of the run into the stack.
+ styleStack.Push( fontRunIndex );
+
+ // Point the next free font run.
+ ++fontRunIndex;
}
else
{
// Pop the top of the stack and set the number of characters of the run.
+ FontDescriptionRun& fontRun = *( markupProcessData.fontRuns.Begin() + styleStack.Pop() );
+ fontRun.characterRun.numberOfCharacters = characterIndex - fontRun.characterRun.characterIndex;
}
} // <i></i>
else if( TokenComparison( XHTML_U_TAG, tag.buffer, tag.length ) )
if( !tag.isEndTag )
{
// Create a new font run.
+ FontDescriptionRun fontRun;
+ fontRun.characterRun.numberOfCharacters = 0u;
+
+ // Fill the run with the parameters.
+ fontRun.characterRun.characterIndex = characterIndex;
+
+ fontRun.weight = TextAbstraction::FontWeight::BOLD;
+
+ fontRun.familyName = NULL;
+ fontRun.familyDefined = false;
+ fontRun.weightDefined = true;
+ fontRun.widthDefined = false;
+ fontRun.slantDefined = false;
+ fontRun.sizeDefined = false;
+
+ // Push the font run in the logical model.
+ markupProcessData.fontRuns.PushBack( fontRun );
+
+ // Push the index of the run into the stack.
+ styleStack.Push( fontRunIndex );
+
+ // Point the next free font run.
+ ++fontRunIndex;
}
else
{
// Pop the top of the stack and set the number of characters of the run.
+ FontDescriptionRun& fontRun = *( markupProcessData.fontRuns.Begin() + styleStack.Pop() );
+ fontRun.characterRun.numberOfCharacters = characterIndex - fontRun.characterRun.characterIndex;
}
} // <b></b>
else if( TokenComparison( XHTML_FONT_TAG, tag.buffer, tag.length ) )
if( !tag.isEndTag )
{
// Create a new font run.
+ FontDescriptionRun fontRun;
+ fontRun.characterRun.numberOfCharacters = 0u;
+
+ // Fill the run with the parameters.
+ fontRun.characterRun.characterIndex = characterIndex;
+
+ fontRun.familyName = NULL;
+ fontRun.familyDefined = false;
+ fontRun.weightDefined = false;
+ fontRun.widthDefined = false;
+ fontRun.slantDefined = false;
+ fontRun.sizeDefined = false;
+
+ ProcessFontTag( tag, fontRun );
+
+ // Push the font run in the logical model.
+ markupProcessData.fontRuns.PushBack( fontRun );
+
+ // Push the index of the run into the stack.
+ styleStack.Push( fontRunIndex );
+
+ // Point the next free font run.
+ ++fontRunIndex;
}
else
{
// Pop the top of the stack and set the number of characters of the run.
+ FontDescriptionRun& fontRun = *( markupProcessData.fontRuns.Begin() + styleStack.Pop() );
+ fontRun.characterRun.numberOfCharacters = characterIndex - fontRun.characterRun.characterIndex;
}
} // <font></font>
else if( TokenComparison( XHTML_SHADOW_TAG, tag.buffer, tag.length ) )
++markupStringBuffer;
}
}
- else if( ( LINE_SEPARATOR_CR == character ) && ( markupStringBuffer + 1u < markupStringEndBuffer ) )
- {
- // Replacing CR+LF end line by LF.
- if( LINE_SEPARATOR_LF == *( markupStringBuffer + 1u ) )
- {
- character = LINE_SEPARATOR_LF;
- ++markupStringBuffer;
- }
- }
const unsigned char numberOfBytes = GetUtf8Length( character );
}
// Resize the model's vectors.
+ if( 0u == fontRunIndex )
+ {
+ markupProcessData.fontRuns.Clear();
+ }
+ else
+ {
+ markupProcessData.fontRuns.Resize( fontRunIndex );
+ }
+
if( 0u == colorRunIndex )
{
markupProcessData.colorRuns.Clear();
// INTERNAL INCLUDES
#include <dali-toolkit/internal/text/color-run.h>
+#include <dali-toolkit/internal/text/font-description-run.h>
namespace Dali
{
*/
struct MarkupProcessData
{
- MarkupProcessData( Vector<ColorRun>& colorRuns )
+MarkupProcessData( Vector<ColorRun>& colorRuns,
+ Vector<FontDescriptionRun>& fontRuns )
: colorRuns( colorRuns ),
+ fontRuns( fontRuns ),
markupProcessedText()
{}
- Vector<ColorRun>& colorRuns;
+ Vector<ColorRun>& colorRuns; ///< The color runs.
+ Vector<FontDescriptionRun>& fontRuns; ///< The font description runs.
- std::string markupProcessedText;
+ std::string markupProcessedText; ///< The mark-up string.
};
/**
{
/**
- * @brief Retrieves the font Id from the font run for a given character's @p index.
+ * @brief Merges the font descriptions to retrieve the font Id for each character.
*
- * If the character's index exceeds the current font run it increases the iterator to get the next one.
- *
- * @param[in] index The character's index.
- * @param[in,out] fontRunIt Iterator to the current font run.
- * @param[in] fontRunEndIt Iterator to one after the last font run.
- *
- * @return The font id.
+ * @param[in] fontDescriptions The font descriptions.
+ * @param[out] fontIds The font id for each character.
+ * @param[in] defaultFontDescription The default font description.
+ * @param[in] defaultPointSize The default font size.
*/
-FontId GetFontId( Length index,
- Vector<FontRun>::ConstIterator& fontRunIt,
- const Vector<FontRun>::ConstIterator& fontRunEndIt )
+void MergeFontDescriptions( const Vector<FontDescriptionRun>& fontDescriptions,
+ Vector<FontId>& fontIds,
+ const TextAbstraction::FontDescription& defaultFontDescription,
+ TextAbstraction::PointSize26Dot6 defaultPointSize )
{
- FontId fontId = 0u;
+ // Get the handle to the font client.
+ TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
- if( fontRunIt != fontRunEndIt )
- {
- const FontRun& fontRun = *fontRunIt;
+ // Pointer to the font id buffer.
+ FontId* fontIdsBuffer = fontIds.Begin();
- if( ( index >= fontRun.characterRun.characterIndex ) &&
- ( index < fontRun.characterRun.characterIndex + fontRun.characterRun.numberOfCharacters ) )
+ // Traverse all the characters.
+ const Length numberOfCharacters = fontIds.Count();
+ for( CharacterIndex index = 0u; index < numberOfCharacters; ++index )
+ {
+ // The default font description and font point size.
+ TextAbstraction::FontDescription fontDescription = defaultFontDescription;
+ TextAbstraction::PointSize26Dot6 fontSize = defaultPointSize;
+ bool defaultFont = true;
+
+ // Traverse all the font descriptions.
+ for( Vector<FontDescriptionRun>::ConstIterator it = fontDescriptions.Begin(),
+ endIt = fontDescriptions.End();
+ it != endIt;
+ ++it )
{
- fontId = fontRun.fontId;
+ // Check whether the character's font is modified by the current font description.
+ const FontDescriptionRun& fontRun = *it;
+ if( ( index >= fontRun.characterRun.characterIndex ) &&
+ ( index < fontRun.characterRun.characterIndex + fontRun.characterRun.numberOfCharacters ) )
+ {
+ if( fontRun.familyDefined )
+ {
+ fontDescription.family = std::string( fontRun.familyName, fontRun.familyLength );
+ defaultFont = false;
+ }
+ if( fontRun.weightDefined )
+ {
+ fontDescription.weight = fontRun.weight;
+ defaultFont = false;
+ }
+ if( fontRun.widthDefined )
+ {
+ fontDescription.width = fontRun.width;
+ defaultFont = false;
+ }
+ if( fontRun.slantDefined )
+ {
+ fontDescription.slant = fontRun.slant;
+ defaultFont = false;
+ }
+ if( fontRun.sizeDefined )
+ {
+ fontSize = fontRun.size;
+ defaultFont = false;
+ }
+ }
}
- if( index + 1u == fontRun.characterRun.characterIndex + fontRun.characterRun.numberOfCharacters )
+ // Get the font id if is not the default font.
+ if( !defaultFont )
{
- // All the characters of the current run have been traversed. Get the next one for the next iteration.
- ++fontRunIt;
+ *( fontIdsBuffer + index ) = fontClient.GetFontId( fontDescription, fontSize );
}
}
-
- return fontId;
}
/**
void MultilanguageSupport::ValidateFonts( const Vector<Character>& text,
const Vector<ScriptRun>& scripts,
+ const Vector<FontDescriptionRun>& fontDescriptions,
+ FontId defaultFontId,
Vector<FontRun>& fonts )
{
+ // Clear any previously validated font.
+ fonts.Clear();
+
DALI_LOG_INFO( gLogFilter, Debug::General, "-->MultilanguageSupport::ValidateFonts\n" );
const Length numberOfCharacters = text.Count();
return;
}
- // Copy the fonts set by application developers.
- const Length numberOfFontRuns = fonts.Count();
- const Vector<FontRun> userSetFonts = fonts;
- fonts.Clear();
-
// Traverse the characters and validate/set the fonts.
// Get the caches.
ValidateFontsPerScript** validFontsPerScriptCacheBuffer = mValidFontsPerScriptCache.Begin();
// Stores the validated font runs.
- fonts.Reserve( numberOfFontRuns );
+ fonts.Reserve( fontDescriptions.Count() );
// Initializes a validated font run.
FontRun currentFontRun;
currentFontRun.characterRun.characterIndex = 0u;
currentFontRun.characterRun.numberOfCharacters = 0u;
currentFontRun.fontId = 0u;
- currentFontRun.isDefault = false;
// Get the font client.
TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
- // Iterators of the font and script runs.
- Vector<FontRun>::ConstIterator fontRunIt = userSetFonts.Begin();
- Vector<FontRun>::ConstIterator fontRunEndIt = userSetFonts.End();
+ // Get the default font description and default size.
+ TextAbstraction::FontDescription defaultFontDescription;
+ TextAbstraction::PointSize26Dot6 defaultPointSize = TextAbstraction::FontClient::DEFAULT_POINT_SIZE;
+ if( defaultFontId > 0u )
+ {
+ fontClient.GetDescription( defaultFontId, defaultFontDescription );
+ defaultPointSize = fontClient.GetPointSize( defaultFontId );
+ }
+
+ // Merge font descriptions
+ Vector<FontId> fontIds;
+ fontIds.Resize( numberOfCharacters, defaultFontId );
+ MergeFontDescriptions( fontDescriptions,
+ fontIds,
+ defaultFontDescription,
+ defaultPointSize );
+
+ const Character* const textBuffer = text.Begin();
+ const FontId* const fontIdsBuffer = fontIds.Begin();
Vector<ScriptRun>::ConstIterator scriptRunIt = scripts.Begin();
Vector<ScriptRun>::ConstIterator scriptRunEndIt = scripts.End();
for( Length index = 0u; index < numberOfCharacters; ++index )
{
// Get the character.
- const Character character = *( text.Begin() + index );
+ const Character character = *( textBuffer + index );
// Get the font for the character.
- FontId fontId = GetFontId( index,
- fontRunIt,
- fontRunEndIt );
+ FontId fontId = *( fontIdsBuffer + index );
// Get the script for the character.
Script script = GetScript( index,
}
// Whether the font being validated is a default one not set by the user.
- const bool isDefault = ( 0u == fontId );
FontId preferredFont = fontId;
- DALI_LOG_INFO( gLogFilter,
- Debug::Verbose,
- " Is a default font : %s\n",
- ( isDefault ? "true" : "false" ) );
+ // Validate if the font set by the user supports the character.
- // The default font point size.
- PointSize26Dot6 pointSize = TextAbstraction::FontClient::DEFAULT_POINT_SIZE;
+ // Check first in the caches.
- if( !isDefault )
+ // The user may have set the default font. Check it. Otherwise check in the valid fonts cache.
+ if( fontId != *( defaultFontPerScriptCacheBuffer + script ) )
{
- // Validate if the font set by the user supports the character.
-
- // Check first in the caches.
+ // Check in the valid fonts cache.
+ ValidateFontsPerScript* validateFontsPerScript = *( validFontsPerScriptCacheBuffer + script );
- // The user may have set the default font. Check it. Otherwise check in the valid fonts cache.
- if( fontId != *( defaultFontPerScriptCacheBuffer + script ) )
+ if( NULL == validateFontsPerScript )
{
- // Check in the valid fonts cache.
- ValidateFontsPerScript* validateFontsPerScript = *( validFontsPerScriptCacheBuffer + script );
-
- if( NULL == validateFontsPerScript )
- {
- validateFontsPerScript = new ValidateFontsPerScript();
+ validateFontsPerScript = new ValidateFontsPerScript();
- *( validFontsPerScriptCacheBuffer + script ) = validateFontsPerScript;
- }
+ *( validFontsPerScriptCacheBuffer + script ) = validateFontsPerScript;
+ }
- if( NULL != validateFontsPerScript )
+ if( NULL != validateFontsPerScript )
+ {
+ if( !validateFontsPerScript->FindValidFont( fontId ) )
{
- if( !validateFontsPerScript->FindValidFont( fontId ) )
- {
- // Use the font client to validate the font.
- GlyphIndex glyphIndex = fontClient.GetGlyphIndex( fontId, character );
+ // Use the font client to validate the font.
+ GlyphIndex glyphIndex = fontClient.GetGlyphIndex( fontId, character );
- // Emojis are present in many monochrome fonts; prefer color by default.
- if( TextAbstraction::EMOJI == script &&
- 0u != glyphIndex )
+ // Emojis are present in many monochrome fonts; prefer color by default.
+ if( ( TextAbstraction::EMOJI == script ) &&
+ ( 0u != glyphIndex ) )
+ {
+ BufferImage bitmap = fontClient.CreateBitmap( fontId, glyphIndex );
+ if( bitmap &&
+ ( Pixel::BGRA8888 != bitmap.GetPixelFormat() ) )
{
- BufferImage bitmap = fontClient.CreateBitmap( fontId, glyphIndex );
- if( bitmap &&
- Pixel::BGRA8888 != bitmap.GetPixelFormat() )
- {
- glyphIndex = 0;
- }
+ glyphIndex = 0u;
}
+ }
- if( 0u == glyphIndex )
+ if( 0u == glyphIndex )
+ {
+ // The font is not valid. Set to zero and a default one will be set.
+ fontId = 0u;
+ }
+ else
+ {
+ // Add the font to the valid font cache.
+
+ // At this point the validated font supports the given character. However, characters
+ // common for all scripts, like white spaces or new paragraph characters, need to be
+ // processed differently.
+ //
+ // i.e. A white space can have assigned a DEVANAGARI script but the font assigned may not
+ // support none of the DEVANAGARI glyphs. This font can't be added to the cache as a valid
+ // font for the DEVANAGARI script but the COMMON one.
+ if( TextAbstraction::IsCommonScript( character ) )
{
- // Get the point size of the current font. It will be used to get a default font id.
- pointSize = fontClient.GetPointSize( fontId );
+ validateFontsPerScript = *( validFontsPerScriptCacheBuffer + TextAbstraction::COMMON );
- // The font is not valid. Set to zero and a default one will be set.
- fontId = 0u;
- }
- else
- {
- // Add the font to the valid font cache.
-
- // At this point the validated font supports the given character. However, characters
- // common for all scripts, like white spaces or new paragraph characters, need to be
- // processed differently.
- //
- // i.e. A white space can have assigned a DEVANAGARI script but the font assigned may not
- // support none of the DEVANAGARI glyphs. This font can't be added to the cache as a valid
- // font for the DEVANAGARI script but the COMMON one.
- if( TextAbstraction::IsCommonScript( character ) )
+ if( NULL == validateFontsPerScript )
{
- validateFontsPerScript = *( validFontsPerScriptCacheBuffer + TextAbstraction::COMMON );
-
- if( NULL == validateFontsPerScript )
- {
- validateFontsPerScript = new ValidateFontsPerScript();
+ validateFontsPerScript = new ValidateFontsPerScript();
- *( validFontsPerScriptCacheBuffer + TextAbstraction::COMMON ) = validateFontsPerScript;
- }
+ *( validFontsPerScriptCacheBuffer + TextAbstraction::COMMON ) = validateFontsPerScript;
}
-
- validateFontsPerScript->mValidFonts.PushBack( fontId );
}
+
+ validateFontsPerScript->mValidFonts.PushBack( fontId );
}
}
}
- } // !isDefault
+ }
// The font has not been validated. Find a default one.
if( 0u == fontId )
bool preferColor = ( TextAbstraction::EMOJI == script );
// Find a fallback-font.
- fontId = fontClient.FindFallbackFont( preferredFont, character, pointSize, preferColor );
+ fontId = fontClient.FindFallbackFont( preferredFont, character, defaultPointSize, preferColor );
// If the system does not support a suitable font, fallback to Latin
if( 0u == fontId )
}
if( 0u == fontId )
{
- fontId = fontClient.FindDefaultFont( UTF32_A, pointSize );
+ fontId = fontClient.FindDefaultFont( UTF32_A, defaultPointSize );
}
// Cache the font.
// The font is now validated.
- if( ( fontId != currentFontRun.fontId ) ||
- ( isDefault != currentFontRun.isDefault ) )
+ if( fontId != currentFontRun.fontId )
{
// 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.isDefault = isDefault;
}
// Add one more character to the run.
Vector<ScriptRun>& scripts );
/**
- * @copydoc Dali::MultilanguageSupport::ValidateFonts( const Vector<Character>& text, const Vector<ScriptRun>& scripts, Vector<FontRun>& fonts )
+ * @copydoc Dali::MultilanguageSupport::ValidateFonts()
*/
void ValidateFonts( const Vector<Character>& text,
const Vector<ScriptRun>& scripts,
+ const Vector<FontDescriptionRun>& fontDescriptions,
+ FontId defaultFontId,
Vector<FontRun>& fonts );
private:
void MultilanguageSupport::ValidateFonts( const Vector<Character>& text,
const Vector<ScriptRun>& scripts,
+ const Vector<FontDescriptionRun>& fontDescriptions,
+ FontId defaultFontId,
Vector<FontRun>& fonts )
{
GetImplementation( *this ).ValidateFonts( text,
scripts,
+ fontDescriptions,
+ defaultFontId,
fonts );
}
// INTERNAL INCLUDES
#include <dali-toolkit/internal/text/font-run.h>
+#include <dali-toolkit/internal/text/font-description-run.h>
#include <dali-toolkit/internal/text/script-run.h>
namespace Dali
/**
* @brief Validates the character's font of the whole text.
*
- * It may update fonts set by application developers.
- *
* This method ensures all characters are going to be rendered using an appropriate font. Provided a valid font
* exists in the platform.
*
*
* @param[in] text Vector of UTF-32 characters.
* @param[in] scripts Vector containing the script runs for the whole text.
- * @param[in,out] fonts Initially contains the fonts set by the application developers. Returns the validated fonts.
+ * @param[in] fontDescriptions The fonts set by the application developers.
+ * @param[in] defaultFontId The default font's id.
+ * @param[out] fonts The validated fonts.
*/
void ValidateFonts( const Vector<Character>& text,
const Vector<ScriptRun>& scripts,
+ const Vector<FontDescriptionRun>& fontDescriptions,
+ FontId defaultFontId,
Vector<FontRun>& fonts );
};
);
const char* FRAGMENT_SHADER_L8 = MAKE_SHADER(
+uniform lowp vec4 uColor;
uniform sampler2D sTexture;
varying mediump vec2 vTexCoord;
varying mediump vec4 vColor;
void main()
{
mediump vec4 color = texture2D( sTexture, vTexCoord );
- gl_FragColor = vec4( vColor.rgb, vColor.a * color.r );
+ gl_FragColor = vec4( vColor.rgb * uColor.rgb, vColor.a * uColor.a * color.r );
}
);
Pixel::Format pixelFormat = mAtlasManager.GetPixelFormat( slot.mAtlasId );
Material material = Material::New( pixelFormat == Pixel::L8 ? mShaderL8 : mShaderRgba );
material.AddTexture( atlas, "sTexture" );
- material.SetBlendMode( BlendingMode::ON );
mAtlasManager.SetMaterial( slot.mAtlasId, material );
}
if( actor.GetRendererCount() )
{
Dali::Renderer renderer( shadowActor.GetRendererAt( 0 ) );
- renderer.SetDepthIndex( renderer.GetDepthIndex() - 1 );
+ int depthIndex = renderer.GetProperty<int>(Dali::Renderer::Property::DEPTH_INDEX);
+ renderer.SetProperty( Dali::Renderer::Property::DEPTH_INDEX, depthIndex - 1 );
shadowActor.SetParentOrigin( ParentOrigin::CENTER );
shadowActor.SetSize( actorSize );
containerActor.Add( shadowActor );
Material material = mGlyphManager.GetMaterial( meshRecord.mAtlasId );
Dali::Renderer renderer = Dali::Renderer::New( quadGeometry, material );
- renderer.SetDepthIndex( DepthIndex::CONTENT + mDepth );
+ renderer.SetProperty( Dali::Renderer::Property::BLENDING_MODE, BlendingMode::ON );
+ renderer.SetProperty( Dali::Renderer::Property::DEPTH_INDEX, DepthIndex::CONTENT + mDepth );
Actor actor = Actor::New();
#if defined(DEBUG_ENABLED)
actor.SetName( "Text renderable actor" );
if( validateFonts )
{
- if( 0u == validFonts.Count() )
- {
- // Copy the requested font defaults received via the property system.
- // These may not be valid i.e. may not contain glyphs for the necessary scripts.
- GetDefaultFonts( validFonts, numberOfCharacters );
- }
+ // Validate the fonts set through the mark-up string.
+ Vector<FontDescriptionRun>& fontDescriptionRuns = mLogicalModel->mFontDescriptionRuns;
+
+ // Get the default font id.
+ const FontId defaultFontId = ( NULL == mFontDefaults ) ? 0u : mFontDefaults->GetFontId( mFontClient );
// Validates the fonts. If there is a character with no assigned font it sets a default one.
// After this call, fonts are validated.
multilanguageSupport.ValidateFonts( utf32Characters,
scripts,
+ fontDescriptionRuns,
+ defaultFontId,
validFonts );
}
}
if( 0u != bidirectionalInfo.Count() )
{
- // This paragraph has right to left text. Some characters may need to be mirrored.
- // TODO: consider if the mirrored string can be stored as well.
-
- textMirrored = GetMirroredText( utf32Characters,
- mirroredUtf32Characters,
- bidirectionalInfo );
-
// Only set the character directions if there is right to left characters.
Vector<CharacterDirection>& directions = mLogicalModel->mCharacterDirections;
directions.Resize( numberOfCharacters );
GetCharactersDirection( bidirectionalInfo,
directions );
+
+ // This paragraph has right to left text. Some characters may need to be mirrored.
+ // TODO: consider if the mirrored string can be stored as well.
+
+ textMirrored = GetMirroredText( utf32Characters,
+ directions,
+ bidirectionalInfo,
+ mirroredUtf32Characters );
}
else
{
void Controller::Impl::RetrieveDefaultInputStyle( InputStyle& inputStyle )
{
- // Set the default text's color.
+ // Sets the default text's color.
inputStyle.textColor = mTextColor;
-}
-void Controller::Impl::GetDefaultFonts( Vector<FontRun>& fonts, Length numberOfCharacters )
-{
+ // Sets the default font's family name, weight, width, slant and size.
if( mFontDefaults )
{
- DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::GetDefaultFonts font family(%s)\n", mFontDefaults->mFontDescription.family.c_str() );
- FontRun fontRun;
- fontRun.characterRun.characterIndex = 0;
- fontRun.characterRun.numberOfCharacters = numberOfCharacters;
- fontRun.fontId = mFontDefaults->GetFontId( mFontClient );
- fontRun.isDefault = true;
+ inputStyle.familyName = mFontDefaults->mFontDescription.family;
+ inputStyle.weight = mFontDefaults->mFontDescription.weight;
+ inputStyle.width = mFontDefaults->mFontDescription.width;
+ inputStyle.slant = mFontDefaults->mFontDescription.slant;
+ inputStyle.size = mFontDefaults->mDefaultPointSize;
- fonts.PushBack( fontRun );
+ inputStyle.familyDefined = mFontDefaults->familyDefined;
+ inputStyle.weightDefined = mFontDefaults->weightDefined;
+ inputStyle.widthDefined = mFontDefaults->widthDefined;
+ inputStyle.slantDefined = mFontDefaults->slantDefined;
+ inputStyle.sizeDefined = mFontDefaults->sizeDefined;
+ }
+ else
+ {
+ inputStyle.familyName.clear();
+ inputStyle.weight = TextAbstraction::FontWeight::NORMAL;
+ inputStyle.width = TextAbstraction::FontWidth::NORMAL;
+ inputStyle.slant = TextAbstraction::FontSlant::NORMAL;
+ inputStyle.size = 0.f;
+
+ inputStyle.familyDefined = false;
+ inputStyle.weightDefined = false;
+ inputStyle.widthDefined = false;
+ inputStyle.slantDefined = false;
+ inputStyle.sizeDefined = false;
}
}
const Vector2 primaryPosition = primaryCursorInfo.primaryPosition + offset;
const Vector2 secondaryPosition = secondaryCursorInfo.primaryPosition + offset;
- mEventData->mDecorator->SetPosition( LEFT_SELECTION_HANDLE, primaryPosition.x, primaryPosition.y, primaryCursorInfo.lineHeight );
+ mEventData->mDecorator->SetPosition( LEFT_SELECTION_HANDLE,
+ primaryPosition.x,
+ primaryCursorInfo.lineOffset + offset.y,
+ primaryCursorInfo.lineHeight );
- mEventData->mDecorator->SetPosition( RIGHT_SELECTION_HANDLE, secondaryPosition.x, secondaryPosition.y, secondaryCursorInfo.lineHeight );
+ mEventData->mDecorator->SetPosition( RIGHT_SELECTION_HANDLE,
+ secondaryPosition.x,
+ secondaryCursorInfo.lineOffset + offset.y,
+ secondaryCursorInfo.lineHeight );
// Cursor to be positioned at end of selection so if selection interrupted and edit mode restarted the cursor will be at end of selection
mEventData->mPrimaryCursorPosition = ( indicesSwapped ) ? mEventData->mLeftSelectionPosition : mEventData->mRightSelectionPosition;
// If there is no font's family set, use the default font.
// Use the current alignment to place the cursor at the beginning, center or end of the box.
+ cursorInfo.lineOffset = 0.f;
cursorInfo.lineHeight = GetDefaultFontLineHeight();
cursorInfo.primaryCursorHeight = cursorInfo.lineHeight;
cursorInfo.isSecondaryCursor = ( !isLastPosition && ( isCurrentRightToLeft != isNextRightToLeft ) ) ||
( isLastPosition && ( isRightToLeftParagraph != isCurrentRightToLeft ) );
- // Set the line height.
+ // Set the line offset and height.
+ cursorInfo.lineOffset = 0.f;
cursorInfo.lineHeight = line.ascender + -line.descender;
// Calculate the primary cursor.
// Sets the grab handle position.
mEventData->mDecorator->SetPosition( GRAB_HANDLE,
cursorPosition.x,
- cursorPosition.y,
+ cursorInfo.lineOffset + offset.y,
cursorInfo.lineHeight );
if( cursorInfo.isSecondaryCursor )
return;
}
- const Vector2 cursorPosition = cursorInfo.primaryPosition + mEventData->mScrollPosition + mAlignmentOffset;
+ const Vector2 offset = mEventData->mScrollPosition + mAlignmentOffset;
+ const Vector2 cursorPosition = cursorInfo.primaryPosition + offset;
// Sets the handle's position.
mEventData->mDecorator->SetPosition( handleType,
cursorPosition.x,
- cursorPosition.y,
+ cursorInfo.lineOffset + offset.y,
cursorInfo.lineHeight );
// If selection handle at start of the text and other at end of the text then all text is selected.
CursorInfo()
: primaryPosition(),
secondaryPosition(),
+ lineOffset( 0.f ),
lineHeight( 0.f ),
primaryCursorHeight( 0.f ),
secondaryCursorHeight( 0.f ),
Vector2 primaryPosition; ///< The primary cursor's position.
Vector2 secondaryPosition; ///< The secondary cursor's position.
+ float lineOffset; ///< The vertical offset where the line containing the cursor starts.
float lineHeight; ///< The height of the line where the cursor is placed.
float primaryCursorHeight; ///< The primary cursor's height.
float secondaryCursorHeight; ///< The secondary cursor's height.
: mFontDescription(),
mFontStyle(),
mDefaultPointSize( 0.f ),
- mFontId( 0u )
+ mFontId( 0u ),
+ familyDefined( false ),
+ weightDefined( false ),
+ widthDefined( false ),
+ slantDefined( false ),
+ sizeDefined( false )
{
// Initially use the default platform font
TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
return mFontId;
}
- TextAbstraction::FontDescription mFontDescription;
- std::string mFontStyle;
- float mDefaultPointSize;
- FontId mFontId;
+ TextAbstraction::FontDescription mFontDescription; ///< The default font's description.
+ std::string mFontStyle; ///< The font's style string set through the property system.
+ float mDefaultPointSize; ///< The default font's point size.
+ FontId mFontId; ///< The font's id of the default font.
+ bool familyDefined:1; ///< Whether the default font's family name is defined.
+ bool weightDefined:1; ///< Whether the default font's weight is defined.
+ bool widthDefined:1; ///< Whether the default font's width is defined.
+ bool slantDefined:1; ///< Whether the default font's slant is defined.
+ bool sizeDefined:1; ///< Whether the default font's point size is defined.
};
struct Controller::Impl
mOperationsPending( NO_OPERATION ),
mMaximumNumberOfCharacters( 50u ),
mRecalculateNaturalSize( true ),
- mUserDefinedFontFamily( false ),
mMarkupProcessorEnabled( false )
{
mLogicalModel = LogicalModel::New();
void RetrieveDefaultInputStyle( InputStyle& inputStyle );
/**
- * @brief Retrieve the default fonts.
- *
- * @param[out] fonts The default font family, style and point sizes.
- * @param[in] numberOfCharacters The number of characters in the logical model.
- */
- void GetDefaultFonts( Dali::Vector<FontRun>& fonts, Length numberOfCharacters );
-
- /**
* @brief Retrieve the line height of the default font.
*/
float GetDefaultFontLineHeight();
Length mMaximumNumberOfCharacters; ///< Maximum number of characters that can be inserted.
bool mRecalculateNaturalSize:1; ///< Whether the natural size needs to be recalculated.
- bool mUserDefinedFontFamily:1; ///< Whether the Font family was set by the user instead of being left as sytem default.
bool mMarkupProcessorEnabled:1; ///< Whether the mark-up procesor is enabled.
};
// EXTERNAL INCLUDES
#include <limits>
+#include <memory.h>
#include <dali/public-api/adaptor-framework/key.h>
#include <dali/integration-api/debug.h>
#include <dali/devel-api/adaptor-framework/clipboard-event-notifier.h>
namespace Text
{
+/**
+ * @brief Adds a new font description run for the selected text.
+ *
+ * The new font parameters are added after the call to this method.
+ *
+ * @param[in] eventData The event data pointer.
+ * @param[in] logicalModel The logical model where to add the new font description run.
+ */
+FontDescriptionRun& UpdateSelectionFontStyleRun( EventData* eventData,
+ LogicalModelPtr logicalModel )
+{
+ const bool handlesCrossed = eventData->mLeftSelectionPosition > eventData->mRightSelectionPosition;
+
+ // Get start and end position of selection
+ const CharacterIndex startOfSelectedText = handlesCrossed ? eventData->mRightSelectionPosition : eventData->mLeftSelectionPosition;
+ const Length lengthOfSelectedText = ( handlesCrossed ? eventData->mLeftSelectionPosition : eventData->mRightSelectionPosition ) - startOfSelectedText;
+
+ // Add the font run.
+ const VectorBase::SizeType numberOfRuns = logicalModel->mFontDescriptionRuns.Count();
+ logicalModel->mFontDescriptionRuns.Resize( numberOfRuns + 1u );
+
+ FontDescriptionRun& fontDescriptionRun = *( logicalModel->mFontDescriptionRuns.Begin() + numberOfRuns );
+
+ fontDescriptionRun.characterRun.characterIndex = startOfSelectedText;
+ fontDescriptionRun.characterRun.numberOfCharacters = lengthOfSelectedText;
+
+ // Recalculate the selection highlight as the metrics may have changed.
+ eventData->mUpdateLeftSelectionPosition = true;
+ eventData->mUpdateRightSelectionPosition = true;
+
+ return fontDescriptionRun;
+}
+
ControllerPtr Controller::New( ControlInterface& controlInterface )
{
return ControllerPtr( new Controller( controlInterface ) );
if( !text.empty() )
{
- MarkupProcessData markupProcessData( mImpl->mLogicalModel->mColorRuns );
+ MarkupProcessData markupProcessData( mImpl->mLogicalModel->mColorRuns,
+ mImpl->mLogicalModel->mFontDescriptionRuns );
Length textSize = 0u;
const uint8_t* utf8 = NULL;
}
}
-void Controller::SetMaximumNumberOfCharacters( int maxCharacters )
+void Controller::SetMaximumNumberOfCharacters( Length maxCharacters )
{
- if( maxCharacters >= 0 )
- {
- mImpl->mMaximumNumberOfCharacters = maxCharacters;
- }
+ mImpl->mMaximumNumberOfCharacters = maxCharacters;
}
int Controller::GetMaximumNumberOfCharacters()
mImpl->mFontDefaults->mFontDescription.family = defaultFontFamily;
DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetDefaultFontFamily %s\n", defaultFontFamily.c_str());
- mImpl->mUserDefinedFontFamily = true;
+ mImpl->mFontDefaults->familyDefined = true;
// Clear the font-specific data
ClearFontData();
return EMPTY_STRING;
}
-void Controller::SetDefaultFontWidth( FontWidth width )
+void Controller::SetDefaultFontWeight( FontWeight weight )
{
if( NULL == mImpl->mFontDefaults )
{
mImpl->mFontDefaults = new FontDefaults();
}
- mImpl->mFontDefaults->mFontDescription.width = width;
+ mImpl->mFontDefaults->mFontDescription.weight = weight;
+ mImpl->mFontDefaults->weightDefined = true;
// Clear the font-specific data
ClearFontData();
mImpl->RequestRelayout();
}
-FontWidth Controller::GetDefaultFontWidth() const
+FontWeight Controller::GetDefaultFontWeight() const
{
if( NULL != mImpl->mFontDefaults )
{
- return mImpl->mFontDefaults->mFontDescription.width;
+ return mImpl->mFontDefaults->mFontDescription.weight;
}
- return TextAbstraction::FontWidth::NORMAL;
+ return TextAbstraction::FontWeight::NORMAL;
}
-void Controller::SetDefaultFontWeight( FontWeight weight )
+void Controller::SetDefaultFontWidth( FontWidth width )
{
if( NULL == mImpl->mFontDefaults )
{
mImpl->mFontDefaults = new FontDefaults();
}
- mImpl->mFontDefaults->mFontDescription.weight = weight;
+ mImpl->mFontDefaults->mFontDescription.width = width;
+ mImpl->mFontDefaults->widthDefined = true;
// Clear the font-specific data
ClearFontData();
mImpl->RequestRelayout();
}
-FontWeight Controller::GetDefaultFontWeight() const
+FontWidth Controller::GetDefaultFontWidth() const
{
if( NULL != mImpl->mFontDefaults )
{
- return mImpl->mFontDefaults->mFontDescription.weight;
+ return mImpl->mFontDefaults->mFontDescription.width;
}
- return TextAbstraction::FontWeight::NORMAL;
+ return TextAbstraction::FontWidth::NORMAL;
}
void Controller::SetDefaultFontSlant( FontSlant slant )
}
mImpl->mFontDefaults->mFontDescription.slant = slant;
+ mImpl->mFontDefaults->slantDefined = true;
// Clear the font-specific data
ClearFontData();
}
mImpl->mFontDefaults->mDefaultPointSize = pointSize;
+ mImpl->mFontDefaults->sizeDefined = true;
unsigned int horizontalDpi( 0u );
unsigned int verticalDpi( 0u );
{
DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::UpdateAfterFontChange");
- if( !mImpl->mUserDefinedFontFamily ) // If user defined font then should not update when system font changes
+ if( !mImpl->mFontDefaults->familyDefined ) // If user defined font then should not update when system font changes
{
DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::UpdateAfterFontChange newDefaultFont(%s)\n", newDefaultFont.c_str() );
ClearFontData();
}
+void Controller::SetInputFontFamily( const std::string& fontFamily )
+{
+ if( NULL != mImpl->mEventData )
+ {
+ mImpl->mEventData->mInputStyle.familyName = fontFamily;
+ mImpl->mEventData->mInputStyle.familyDefined = true;
+
+ if( EventData::SELECTING == mImpl->mEventData->mState )
+ {
+ FontDescriptionRun& fontDescriptionRun = UpdateSelectionFontStyleRun( mImpl->mEventData,
+ mImpl->mLogicalModel );
+
+ fontDescriptionRun.familyLength = fontFamily.size();
+ fontDescriptionRun.familyName = new char[fontDescriptionRun.familyLength];
+ memcpy( fontDescriptionRun.familyName, fontFamily.c_str(), fontDescriptionRun.familyLength );
+ fontDescriptionRun.familyDefined = true;
+
+ // The memory allocated for the font family name is freed when the font description is removed from the logical model.
+
+ // Request to relayout.
+ mImpl->mOperationsPending = ALL_OPERATIONS;
+ mImpl->mRecalculateNaturalSize = true;
+ mImpl->RequestRelayout();
+
+ // As the font changes, recalculate the handle positions is needed.
+ mImpl->mEventData->mUpdateLeftSelectionPosition = true;
+ mImpl->mEventData->mUpdateRightSelectionPosition = true;
+ mImpl->mEventData->mScrollAfterUpdatePosition = true;
+ }
+ }
+}
+
+const std::string& Controller::GetInputFontFamily() const
+{
+ if( NULL != mImpl->mEventData )
+ {
+ return mImpl->mEventData->mInputStyle.familyName;
+ }
+
+ // Return the default font's family if there is no EventData.
+ return GetDefaultFontFamily();
+}
+
+void Controller::SetInputFontStyle( const std::string& fontStyle )
+{
+ if( NULL != mImpl->mEventData )
+ {
+ mImpl->mEventData->mInputStyle.fontStyle = fontStyle;
+ }
+}
+
+const std::string& Controller::GetInputFontStyle() const
+{
+ if( NULL != mImpl->mEventData )
+ {
+ return mImpl->mEventData->mInputStyle.fontStyle;
+ }
+
+ // Return the default font's style if there is no EventData.
+ return GetDefaultFontStyle();
+}
+
+void Controller::SetInputFontWeight( FontWeight weight )
+{
+ if( NULL != mImpl->mEventData )
+ {
+ mImpl->mEventData->mInputStyle.weight = weight;
+ mImpl->mEventData->mInputStyle.weightDefined = true;
+
+ if( EventData::SELECTING == mImpl->mEventData->mState )
+ {
+ FontDescriptionRun& fontDescriptionRun = UpdateSelectionFontStyleRun( mImpl->mEventData,
+ mImpl->mLogicalModel );
+
+ fontDescriptionRun.weight = weight;
+ fontDescriptionRun.weightDefined = true;
+
+ // Request to relayout.
+ mImpl->mOperationsPending = ALL_OPERATIONS;
+ mImpl->mRecalculateNaturalSize = true;
+ mImpl->RequestRelayout();
+
+ // As the font might change, recalculate the handle positions is needed.
+ mImpl->mEventData->mUpdateLeftSelectionPosition = true;
+ mImpl->mEventData->mUpdateRightSelectionPosition = true;
+ mImpl->mEventData->mScrollAfterUpdatePosition = true;
+ }
+ }
+}
+
+FontWeight Controller::GetInputFontWeight() const
+{
+ if( NULL != mImpl->mEventData )
+ {
+ return mImpl->mEventData->mInputStyle.weight;
+ }
+
+ return GetDefaultFontWeight();
+}
+
+void Controller::SetInputFontWidth( FontWidth width )
+{
+ if( NULL != mImpl->mEventData )
+ {
+ mImpl->mEventData->mInputStyle.width = width;
+ mImpl->mEventData->mInputStyle.widthDefined = true;
+
+ if( EventData::SELECTING == mImpl->mEventData->mState )
+ {
+ FontDescriptionRun& fontDescriptionRun = UpdateSelectionFontStyleRun( mImpl->mEventData,
+ mImpl->mLogicalModel );
+
+ fontDescriptionRun.width = width;
+ fontDescriptionRun.widthDefined = true;
+
+ // Request to relayout.
+ mImpl->mOperationsPending = ALL_OPERATIONS;
+ mImpl->mRecalculateNaturalSize = true;
+ mImpl->RequestRelayout();
+
+ // As the font might change, recalculate the handle positions is needed.
+ mImpl->mEventData->mUpdateLeftSelectionPosition = true;
+ mImpl->mEventData->mUpdateRightSelectionPosition = true;
+ mImpl->mEventData->mScrollAfterUpdatePosition = true;
+ }
+ }
+}
+
+FontWidth Controller::GetInputFontWidth() const
+{
+ if( NULL != mImpl->mEventData )
+ {
+ return mImpl->mEventData->mInputStyle.width;
+ }
+
+ return GetDefaultFontWidth();
+}
+
+void Controller::SetInputFontSlant( FontSlant slant )
+{
+ if( NULL != mImpl->mEventData )
+ {
+ mImpl->mEventData->mInputStyle.slant = slant;
+ mImpl->mEventData->mInputStyle.slantDefined = true;
+
+ if( EventData::SELECTING == mImpl->mEventData->mState )
+ {
+ FontDescriptionRun& fontDescriptionRun = UpdateSelectionFontStyleRun( mImpl->mEventData,
+ mImpl->mLogicalModel );
+
+ fontDescriptionRun.slant = slant;
+ fontDescriptionRun.slantDefined = true;
+
+ // Request to relayout.
+ mImpl->mOperationsPending = ALL_OPERATIONS;
+ mImpl->mRecalculateNaturalSize = true;
+ mImpl->RequestRelayout();
+
+ // As the font might change, recalculate the handle positions is needed.
+ mImpl->mEventData->mUpdateLeftSelectionPosition = true;
+ mImpl->mEventData->mUpdateRightSelectionPosition = true;
+ mImpl->mEventData->mScrollAfterUpdatePosition = true;
+ }
+ }
+}
+
+FontSlant Controller::GetInputFontSlant() const
+{
+ if( NULL != mImpl->mEventData )
+ {
+ return mImpl->mEventData->mInputStyle.slant;
+ }
+
+ return GetDefaultFontSlant();
+}
+
+void Controller::SetInputFontPointSize( float size )
+{
+ if( NULL != mImpl->mEventData )
+ {
+ mImpl->mEventData->mInputStyle.size = size;
+
+ if( EventData::SELECTING == mImpl->mEventData->mState )
+ {
+ FontDescriptionRun& fontDescriptionRun = UpdateSelectionFontStyleRun( mImpl->mEventData,
+ mImpl->mLogicalModel );
+
+ fontDescriptionRun.size = static_cast<PointSize26Dot6>( size * 64.f );
+ fontDescriptionRun.sizeDefined = true;
+
+ // Request to relayout.
+ mImpl->mOperationsPending = ALL_OPERATIONS;
+ mImpl->mRecalculateNaturalSize = true;
+ mImpl->RequestRelayout();
+
+ // As the font might change, recalculate the handle positions is needed.
+ mImpl->mEventData->mUpdateLeftSelectionPosition = true;
+ mImpl->mEventData->mUpdateRightSelectionPosition = true;
+ mImpl->mEventData->mScrollAfterUpdatePosition = true;
+ }
+ }
+}
+
+float Controller::GetInputFontPointSize() const
+{
+ if( NULL != mImpl->mEventData )
+ {
+ return mImpl->mEventData->mInputStyle.size;
+ }
+
+ // Return the default font's point size if there is no EventData.
+ return GetDefaultPointSize();
+}
+
void Controller::SetEnableCursorBlink( bool enable )
{
DALI_ASSERT_DEBUG( NULL != mImpl->mEventData && "TextInput disabled" );
mImpl->mControlInterface.TextChanged();
}
- return false;
+ return true;
}
void Controller::InsertText( const std::string& text, Controller::InsertType type )
// The cursor position.
CharacterIndex& cursorIndex = mImpl->mEventData->mPrimaryCursorPosition;
- // Updates the text style runs.
+ // Update the text's style.
+
+ // Updates the text style runs by adding characters.
mImpl->mLogicalModel->UpdateTextStyleRuns( cursorIndex, maxSizeOfNewText );
// Get the character index from the cursor index.
// Whether to add a new text color run.
const bool addColorRun = style.textColor != mImpl->mEventData->mInputStyle.textColor;
+ // Whether to add a new font run.
+ const bool addFontNameRun = style.familyName != mImpl->mEventData->mInputStyle.familyName;
+ const bool addFontWeightRun = style.weight != mImpl->mEventData->mInputStyle.weight;
+ const bool addFontWidthRun = style.width != mImpl->mEventData->mInputStyle.width;
+ const bool addFontSlantRun = style.slant != mImpl->mEventData->mInputStyle.slant;
+ const bool addFontSizeRun = style.size != mImpl->mEventData->mInputStyle.size;
+
// Add style runs.
if( addColorRun )
{
colorRun.characterRun.numberOfCharacters = maxSizeOfNewText;
}
+ if( addFontNameRun ||
+ addFontWeightRun ||
+ addFontWidthRun ||
+ addFontSlantRun ||
+ addFontSizeRun )
+ {
+ const VectorBase::SizeType numberOfRuns = mImpl->mLogicalModel->mFontDescriptionRuns.Count();
+ mImpl->mLogicalModel->mFontDescriptionRuns.Resize( numberOfRuns + 1u );
+
+ FontDescriptionRun& fontDescriptionRun = *( mImpl->mLogicalModel->mFontDescriptionRuns.Begin() + numberOfRuns );
+
+ if( addFontNameRun )
+ {
+ fontDescriptionRun.familyLength = mImpl->mEventData->mInputStyle.familyName.size();
+ fontDescriptionRun.familyName = new char[fontDescriptionRun.familyLength];
+ memcpy( fontDescriptionRun.familyName, mImpl->mEventData->mInputStyle.familyName.c_str(), fontDescriptionRun.familyLength );
+ fontDescriptionRun.familyDefined = true;
+
+ // The memory allocated for the font family name is freed when the font description is removed from the logical model.
+ }
+
+ if( addFontWeightRun )
+ {
+ fontDescriptionRun.weight = mImpl->mEventData->mInputStyle.weight;
+ fontDescriptionRun.weightDefined = true;
+ }
+
+ if( addFontWidthRun )
+ {
+ fontDescriptionRun.width = mImpl->mEventData->mInputStyle.width;
+ fontDescriptionRun.widthDefined = true;
+ }
+
+ if( addFontSlantRun )
+ {
+ fontDescriptionRun.slant = mImpl->mEventData->mInputStyle.slant;
+ fontDescriptionRun.slantDefined = true;
+ }
+
+ if( addFontSizeRun )
+ {
+ fontDescriptionRun.size = static_cast<PointSize26Dot6>( mImpl->mEventData->mInputStyle.size * 64.f );
+ fontDescriptionRun.sizeDefined = true;
+ }
+
+ fontDescriptionRun.characterRun.characterIndex = cursorIndex;
+ fontDescriptionRun.characterRun.numberOfCharacters = maxSizeOfNewText;
+ }
+
// Insert at current cursor position.
Vector<Character>& modifyText = mImpl->mLogicalModel->mText;
void Controller::ClearStyleData()
{
mImpl->mLogicalModel->mColorRuns.Clear();
+ mImpl->mLogicalModel->ClearFontDescriptionRuns();
}
Controller::Controller( ControlInterface& controlInterface )
*
* @param[in] maxCharacters maximum number of characters to be accepted
*/
- void SetMaximumNumberOfCharacters( int maxCharacters );
+ void SetMaximumNumberOfCharacters( Length maxCharacters );
/**
* @brief Sets the maximum number of characters that can be inserted into the TextModel
const std::string& GetDefaultFontStyle() const;
/**
- * @brief Sets the default font width.
+ * @brief Sets the default font weight.
*
- * @param[in] width The font width.
+ * @param[in] weight The font weight.
*/
- void SetDefaultFontWidth( FontWidth width );
+ void SetDefaultFontWeight( FontWeight weight );
/**
- * @brief Retrieves the default font width.
+ * @brief Retrieves the default font weight.
*
- * @return The default font width.
+ * @return The default font weight.
*/
- FontWidth GetDefaultFontWidth() const;
+ FontWeight GetDefaultFontWeight() const;
/**
- * @brief Sets the default font weight.
+ * @brief Sets the default font width.
*
- * @param[in] weight The font weight.
+ * @param[in] width The font width.
*/
- void SetDefaultFontWeight( FontWeight weight );
+ void SetDefaultFontWidth( FontWidth width );
/**
- * @brief Retrieves the default font weight.
+ * @brief Retrieves the default font width.
*
- * @return The default font weight.
+ * @return The default font width.
*/
- FontWeight GetDefaultFontWeight() const;
+ FontWidth GetDefaultFontWidth() const;
/**
* @brief Sets the default font slant.
const Vector4& GetInputColor() const;
/**
+ * @brief Sets the input text's font family name.
+ *
+ * @param[in] fontFamily The text's font family name.
+ */
+ void SetInputFontFamily( const std::string& fontFamily );
+
+ /**
+ * @brief Retrieves the input text's font family name.
+ *
+ * @return The input text's font family name.
+ */
+ const std::string& GetInputFontFamily() const;
+
+ /**
+ * @brief Sets the input text's font style.
+ *
+ * @param[in] fontStyle The input text's font style.
+ */
+ void SetInputFontStyle( const std::string& fontStyle );
+
+ /**
+ * @brief Retrieves the input text's font style.
+ *
+ * @return The input text's font style.
+ */
+ const std::string& GetInputFontStyle() const;
+
+ /**
+ * @brief Sets the input font's weight.
+ *
+ * @param[in] weight The input font's weight.
+ */
+ void SetInputFontWeight( FontWeight weight );
+
+ /**
+ * @brief Retrieves the input font's weight.
+ *
+ * @return The input font's weight.
+ */
+ FontWeight GetInputFontWeight() const;
+
+ /**
+ * @brief Sets the input font's width.
+ *
+ * @param[in] width The input font's width.
+ */
+ void SetInputFontWidth( FontWidth width );
+
+ /**
+ * @brief Retrieves the input font's width.
+ *
+ * @return The input font's width.
+ */
+ FontWidth GetInputFontWidth() const;
+
+ /**
+ * @brief Sets the input font's slant.
+ *
+ * @param[in] slant The input font's slant.
+ */
+ void SetInputFontSlant( FontSlant slant );
+
+ /**
+ * @brief Retrieves the input font's slant.
+ *
+ * @return The input font's slant.
+ */
+ FontSlant GetInputFontSlant() const;
+
+ /**
+ * @brief Sets the input font's point size.
+ *
+ * @param[in] size The input font's point size.
+ */
+ void SetInputFontPointSize( float size );
+
+ /**
+ * @brief Retrieves the input font's point size.
+ *
+ * @return The input font's point size.
+ */
+ float GetInputFontPointSize() const;
+
+ /**
* @brief Called to enable/disable cursor blink.
*
* @note Only editable controls should calls this.
--- /dev/null
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+// FILE HEADER
+#include <dali-toolkit/internal/text/text-font-style.h>
+
+// EXTERNAL INCLUDES
+#include <dali/integration-api/debug.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/devel-api/builder/json-parser.h>
+#include <dali-toolkit/devel-api/builder/tree-node.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+namespace
+{
+const std::string STYLE_KEY( "style" );
+const std::string WEIGHT_KEY( "weight" );
+const std::string WIDTH_KEY( "width" );
+const std::string SLANT_KEY( "slant" );
+const std::string EMPTY_STRING( "" );
+
+#if defined(DEBUG_ENABLED)
+Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Concise, true, "LOG_TEXT_CONTROLS");
+#endif
+
+} // namespace
+
+/**
+ * @brief Creates a map with pairs 'key,value' with the font's style parameters.
+ *
+ * @param[in] node Data structure with the font's style parameters.
+ * @param[out] map A map with the font's style parameters.
+ *
+ */
+void CreateFontStyleMap( const TreeNode* const node, Property::Map& map )
+{
+ switch( node->GetType() )
+ {
+ case TreeNode::IS_NULL:
+ case TreeNode::OBJECT:
+ case TreeNode::ARRAY: // FALL THROUGH
+ {
+ break;
+ }
+ case TreeNode::STRING:
+ {
+ map.Insert( node->GetName(), Property::Value( node->GetString() ) );
+ break;
+ }
+ case TreeNode::INTEGER:
+ case TreeNode::FLOAT:
+ case TreeNode::BOOLEAN: // FALL THROUGH
+ {
+ break;
+ }
+ }
+
+ for( TreeNode::ConstIterator it = node->CBegin(), endIt = node->CEnd(); it != endIt; ++it )
+ {
+ const TreeNode::KeyNodePair& pair = *it;
+ CreateFontStyleMap( &pair.second, map );
+ }
+}
+
+/**
+ * @brief Parses the font's style string.
+ *
+ * @param[in] style The font's style string.
+ * @param[out] map A map with the font's style parameters.
+ *
+ */
+void ParseFontStyleString( const std::string& style, Property::Map& map )
+{
+ Toolkit::JsonParser parser = Toolkit::JsonParser::New();
+
+ if( parser.Parse( style ) )
+ {
+ const TreeNode* const node = parser.GetRoot();
+
+ CreateFontStyleMap( node, map );
+ }
+}
+
+void SetFontStyleProperty( ControllerPtr controller, const Property::Value& value, FontStyle::Type type )
+{
+ if( controller )
+ {
+ const std::string style = value.Get< std::string >();
+ DALI_LOG_INFO( gLogFilter, Debug::General, "Text Control %p FONT_STYLE %s\n", controller.Get(), style.c_str() );
+
+ switch( type )
+ {
+ case FontStyle::DEFAULT:
+ {
+ // Stores the default font's style string to be recovered by the GetFontStyleProperty() function.
+ controller->SetDefaultFontStyle( style );
+ break;
+ }
+ case FontStyle::INPUT:
+ {
+ // Stores the input font's style string to be recovered by the GetFontStyleProperty() function.
+ controller->SetInputFontStyle( style );
+ break;
+ }
+ }
+
+ // Parses and applies the style.
+ Property::Map map;
+ ParseFontStyleString( style, map );
+
+ if( !map.Empty() )
+ {
+ /// Weight key
+ Property::Value* weightValue = map.Find( WEIGHT_KEY );
+
+ FontWeight weight = TextAbstraction::FontWeight::NORMAL;
+ const bool weightDefined = weightValue != NULL;
+ if( weightDefined )
+ {
+ const std::string weightStr = weightValue->Get<std::string>();
+
+ Scripting::GetEnumeration< FontWeight >( weightStr.c_str(),
+ FONT_WEIGHT_STRING_TABLE,
+ FONT_WEIGHT_STRING_TABLE_COUNT,
+ weight );
+ }
+
+ /// Width key
+ Property::Value* widthValue = map.Find( WIDTH_KEY );
+
+ FontWidth width = TextAbstraction::FontWidth::NORMAL;
+ const bool widthDefined = widthValue != NULL;
+ if( widthDefined )
+ {
+ const std::string widthStr = widthValue->Get<std::string>();
+
+ Scripting::GetEnumeration< FontWidth >( widthStr.c_str(),
+ FONT_WIDTH_STRING_TABLE,
+ FONT_WIDTH_STRING_TABLE_COUNT,
+ width );
+ }
+
+ /// Slant key
+ Property::Value* slantValue = map.Find( SLANT_KEY );
+
+ FontSlant slant = TextAbstraction::FontSlant::NORMAL;
+ const bool slantDefined = slantValue != NULL;
+ if( slantDefined )
+ {
+ const std::string slantStr = slantValue->Get<std::string>();
+
+ Scripting::GetEnumeration< FontSlant >( slantStr.c_str(),
+ FONT_SLANT_STRING_TABLE,
+ FONT_SLANT_STRING_TABLE_COUNT,
+ slant );
+ }
+
+ switch( type )
+ {
+ case FontStyle::DEFAULT:
+ {
+ // Sets the default font's style values.
+ if( weightDefined && ( controller->GetDefaultFontWeight() != weight ) )
+ {
+ controller->SetDefaultFontWeight( weight );
+ }
+
+ if( widthDefined && ( controller->GetDefaultFontWidth() != width ) )
+ {
+ controller->SetDefaultFontWidth( width );
+ }
+
+ if( slantDefined && ( controller->GetDefaultFontSlant() != slant ) )
+ {
+ controller->SetDefaultFontSlant( slant );
+ }
+ break;
+ }
+ case FontStyle::INPUT:
+ {
+ // Sets the input font's style values.
+ if( weightDefined && ( controller->GetInputFontWeight() != weight ) )
+ {
+ controller->SetInputFontWeight( weight );
+ }
+
+ if( widthDefined && ( controller->GetInputFontWidth() != width ) )
+ {
+ controller->SetInputFontWidth( width );
+ }
+
+ if( slantDefined && ( controller->GetInputFontSlant() != slant ) )
+ {
+ controller->SetInputFontSlant( slant );
+ }
+ break;
+ }
+ }
+ }
+ }
+}
+
+void GetFontStyleProperty( ControllerPtr controller, Property::Value& value, FontStyle::Type type )
+{
+ if( controller )
+ {
+ switch( type )
+ {
+ case FontStyle::DEFAULT:
+ {
+ value = controller->GetDefaultFontStyle();
+ break;
+ }
+ case FontStyle::INPUT:
+ {
+ value = controller->GetInputFontStyle();
+ break;
+ }
+ }
+ }
+}
+
+FontWeight StringToWeight( const char* const weightStr )
+{
+ FontWeight weight = TextAbstraction::FontWeight::NORMAL;
+ Scripting::GetEnumeration<FontWeight>( weightStr,
+ FONT_WEIGHT_STRING_TABLE,
+ FONT_WEIGHT_STRING_TABLE_COUNT,
+ weight );
+
+ return weight;
+}
+
+FontWidth StringToWidth( const char* const widthStr )
+{
+ FontWidth width = TextAbstraction::FontWidth::NORMAL;
+ Scripting::GetEnumeration<FontWidth>( widthStr,
+ FONT_WIDTH_STRING_TABLE,
+ FONT_WIDTH_STRING_TABLE_COUNT,
+ width );
+
+ return width;
+}
+
+FontSlant StringToSlant( const char* const slantStr )
+{
+ FontSlant slant = TextAbstraction::FontSlant::NORMAL;
+ Scripting::GetEnumeration<FontSlant>( slantStr,
+ FONT_SLANT_STRING_TABLE,
+ FONT_SLANT_STRING_TABLE_COUNT,
+ slant );
+
+ return slant;
+}
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
#define __DALI_TOOLKIT_INTERNAL_TEXT_FONT_STYLE_H__
/*
- * Copyright (c) 2015 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2016 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.
namespace Text
{
-const Scripting::StringEnum FONT_WIDTH_STRING_TABLE[] =
-{
- { "ultraCondensed", TextAbstraction::FontWidth::ULTRA_CONDENSED },
- { "extraCondensed", TextAbstraction::FontWidth::EXTRA_CONDENSED },
- { "condensed", TextAbstraction::FontWidth::CONDENSED },
- { "semiCondensed", TextAbstraction::FontWidth::SEMI_CONDENSED },
- { "normal", TextAbstraction::FontWidth::NORMAL },
- { "semiExpanded", TextAbstraction::FontWidth::SEMI_EXPANDED },
- { "expanded", TextAbstraction::FontWidth::EXPANDED },
- { "extraExpanded", TextAbstraction::FontWidth::EXTRA_EXPANDED },
- { "ultraExpanded", TextAbstraction::FontWidth::ULTRA_EXPANDED },
-};
-const unsigned int FONT_WIDTH_STRING_TABLE_COUNT = sizeof( FONT_WIDTH_STRING_TABLE ) / sizeof( FONT_WIDTH_STRING_TABLE[0] );
-
const Scripting::StringEnum FONT_WEIGHT_STRING_TABLE[] =
{
{ "thin", TextAbstraction::FontWeight::THIN },
};
const unsigned int FONT_WEIGHT_STRING_TABLE_COUNT = sizeof( FONT_WEIGHT_STRING_TABLE ) / sizeof( FONT_WEIGHT_STRING_TABLE[0] );
+const Scripting::StringEnum FONT_WIDTH_STRING_TABLE[] =
+{
+ { "ultraCondensed", TextAbstraction::FontWidth::ULTRA_CONDENSED },
+ { "extraCondensed", TextAbstraction::FontWidth::EXTRA_CONDENSED },
+ { "condensed", TextAbstraction::FontWidth::CONDENSED },
+ { "semiCondensed", TextAbstraction::FontWidth::SEMI_CONDENSED },
+ { "normal", TextAbstraction::FontWidth::NORMAL },
+ { "semiExpanded", TextAbstraction::FontWidth::SEMI_EXPANDED },
+ { "expanded", TextAbstraction::FontWidth::EXPANDED },
+ { "extraExpanded", TextAbstraction::FontWidth::EXTRA_EXPANDED },
+ { "ultraExpanded", TextAbstraction::FontWidth::ULTRA_EXPANDED },
+};
+const unsigned int FONT_WIDTH_STRING_TABLE_COUNT = sizeof( FONT_WIDTH_STRING_TABLE ) / sizeof( FONT_WIDTH_STRING_TABLE[0] );
+
const Scripting::StringEnum FONT_SLANT_STRING_TABLE[] =
{
{ "normal", TextAbstraction::FontSlant::NORMAL },
};
const unsigned int FONT_SLANT_STRING_TABLE_COUNT = sizeof( FONT_SLANT_STRING_TABLE ) / sizeof( FONT_SLANT_STRING_TABLE[0] );
+namespace FontStyle
+{
+ enum Type
+ {
+ DEFAULT, ///< The default font's style.
+ INPUT ///< The input font's style.
+ };
+};
+
/**
* @brief Sets the font's style property.
*
* @param[in] value The value of the font's style.
*
*/
-void SetFontStyleProperty( ControllerPtr controller, const Property::Value& value );
+void SetFontStyleProperty( ControllerPtr controller, const Property::Value& value, FontStyle::Type type );
/**
* @brief Retrieves the font's style property.
* @param[in] controller The text's controller.
* @param[out] value The value of the font's style.
*/
-void GetFontStyleProperty( ControllerPtr controller, Property::Value& value );
+void GetFontStyleProperty( ControllerPtr controller, Property::Value& value, FontStyle::Type type );
+
+/**
+ * @brief Converts a weight string into @e FontWeight.
+ *
+ * @param[in] weightStr The weight string. Must end with '\0'.
+ *
+ * @return The @e FontWeight value corresponding to the string.
+ */
+FontWeight StringToWeight( const char* const weightStr );
+/**
+ * @brief Converts a width string into @e FontWidth.
+ *
+ * @param[in] widthStr The width string. Must end with '\0'.
+ *
+ * @return The @e FontWidth value corresponding to the string.
+ */
+FontWidth StringToWidth( const char* const widthStr );
+
+/**
+ * @brief Converts a slant string into @e FontSlant.
+ *
+ * @param[in] slantStr The slant string. Must end with '\0'.
+ *
+ * @return The @e FontSlant value corresponding to the string.
+ */
+FontSlant StringToSlant( const char* const slantStr );
} // namespace Text
} // namespace Toolkit
}
mCurrentRenderer = Renderer::New( geometry, material );
- mCurrentRenderer.SetDepthIndex( depth );
+ mCurrentRenderer.SetProperty( Renderer::Property::DEPTH_INDEX, depth );
Self().AddRenderer( mCurrentRenderer );
}
Geometry geometry = mCurrentRenderer.GetGeometry();
mTargetRenderer = Renderer::New( geometry, material );
- mTargetRenderer.SetDepthIndex( mCurrentRenderer.GetDepthIndex() );
+ int depthIndex = mCurrentRenderer.GetProperty<int>(Renderer::Property::DEPTH_INDEX);
+ mTargetRenderer.SetProperty( Dali::Renderer::Property::DEPTH_INDEX, depthIndex );
for( size_t i = 0; i < mBoxes.size(); ++i )
{
class AccessibilityManager;
}
/**
- * @addtogroup dali_toolkit_accessibility_manager
+ * @addtogroup dali_toolkit_managers
* @{
*/
/**
- * @brief Manages registration of actors in a accessibility focus chain and changing the
+ * @brief Manages registration of actors in an accessibility focus chain and changing the
* focused actor within that chain.
*
* This class provides the functionality of registering the focus order and description
* | focusChanged | @ref FocusChangedSignal() |
* | focusOvershot | @ref FocusOvershotSignal() |
* | focusedActorActivated | @ref FocusedActorActivatedSignal() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API AccessibilityManager : public BaseHandle
{
* @brief Accessibility Action Signal.
*
* The connected signal callback should return true if handled.
+ * @SINCE_1_0.0
*/
- typedef Signal< bool ( AccessibilityManager& ) > AccessibilityActionSignalType; ///< Generic signal type
- typedef Signal< bool ( AccessibilityManager&, const Dali::TouchEvent& )> AccessibilityActionScrollSignalType; ///< Scroll signal type
+ typedef Signal< bool ( AccessibilityManager& ) > AccessibilityActionSignalType; ///< Generic signal type @SINCE_1_0.0
+ typedef Signal< bool ( AccessibilityManager&, const Dali::TouchEvent& )> AccessibilityActionScrollSignalType; ///< Scroll signal type @SINCE_1_0.0
/**
* @brief Accessibility needs four information which will be read by screen-reader.
*
* Reading order : Label -> Trait -> Optional (Value and Hint)
+ * @SINCE_1_0.0
*/
enum AccessibilityAttribute
{
- ACCESSIBILITY_LABEL = 0, ///< Simple text which contained in ui-control
- ACCESSIBILITY_TRAIT, ///< Description of ui-control trait
- ACCESSIBILITY_VALUE, ///< Current value of ui-control (Optional)
- ACCESSIBILITY_HINT, ///< Hint for action (Optional)
- ACCESSIBILITY_ATTRIBUTE_NUM ///< Number of attributes
+ ACCESSIBILITY_LABEL = 0, ///< Simple text which contained in ui-control @SINCE_1_0.0
+ ACCESSIBILITY_TRAIT, ///< Description of ui-control trait @SINCE_1_0.0
+ ACCESSIBILITY_VALUE, ///< Current value of ui-control (Optional) @SINCE_1_0.0
+ ACCESSIBILITY_HINT, ///< Hint for action (Optional) @SINCE_1_0.0
+ ACCESSIBILITY_ATTRIBUTE_NUM ///< Number of attributes @SINCE_1_0.0
};
/**
* @brief Overshoot direction.
+ * @SINCE_1_0.0
*/
enum FocusOvershotDirection
{
- OVERSHOT_PREVIOUS = -1, ///< Try to move previous of the first actor
- OVERSHOT_NEXT = 1, ///< Try to move next of the last actor
+ OVERSHOT_PREVIOUS = -1, ///< Try to move previous of the first actor @SINCE_1_0.0
+ OVERSHOT_NEXT = 1, ///< Try to move next of the last actor @SINCE_1_0.0
};
public:
/// @brief Focus changed signal
+ /// @SINCE_1_0.0
typedef Signal< void ( Actor, Actor ) > FocusChangedSignalType;
/// @brief Focus overshooted signal
+ /// @SINCE_1_0.0
typedef Signal< void ( Actor, FocusOvershotDirection ) > FocusOvershotSignalType;
/// @brief Focused actor activated signal
+ /// @SINCE_1_0.0
typedef Signal< void ( Actor ) > FocusedActorActivatedSignalType;
/**
* @brief Create a AccessibilityManager handle; this can be initialised with AccessibilityManager::New().
*
* Calling member functions with an uninitialised handle is not allowed.
+ * @SINCE_1_0.0
*/
AccessibilityManager();
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~AccessibilityManager();
/**
* @brief Get the singleton of AccessibilityManager object.
*
+ * @SINCE_1_0.0
* @return A handle to the AccessibilityManager control.
*/
static AccessibilityManager Get();
/**
* @brief Set the information of the specified actor's accessibility attribute.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor the text to be set with
* @param type The attribute type the text to be set with
* @param text The text for the actor's accessibility information
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
void SetAccessibilityAttribute(Actor actor, AccessibilityAttribute type, const std::string& text);
/**
* @brief Get the text of the specified actor's accessibility attribute.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be queried
* @param type The attribute type to be queried
* @return The text of the actor's accessibility information
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
std::string GetAccessibilityAttribute(Actor actor, AccessibilityAttribute type) const;
* description but with no focus order being set yet) and therefore
* that actor is not focusable.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor the focus order to be set with
* @param order The focus order of the actor
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
void SetFocusOrder(Actor actor, const unsigned int order);
* When the focus order is 0, it means the focus order of the actor
* is undefined.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be queried
* @return The focus order of the actor
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
unsigned int GetFocusOrder(Actor actor) const;
* 1 where FOLast is the focus order of the very last control in the
* focus chain.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return The focus order of the actor
+ * @pre The AccessibilityManager has been initialized.
*/
unsigned int GenerateNewFocusOrder() const;
/**
* @brief Get the actor that has the specified focus order.
*
- * It will return an empty handle if the actor is not in the stage
- * or has a focus order of 0.
+ * It will return an empty handle if no actor in the stage
+ * has the specified focus order.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @param order The focus order of the actor
*
* @return The actor that has the specified focus order or an empty
* handle if no actor in the stage has the specified focus order.
+ * @pre The AccessibilityManager has been initialized.
*/
Actor GetActorByFocusOrder(const unsigned int order);
* have a defined focus order and must be focusable, visible and in
* the stage.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be focused
* @return Whether the focus is successful or not
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
bool SetCurrentFocusActor(Actor actor);
/**
* @brief Get the current focused actor.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return A handle to the current focused actor or an empty handle if no actor is focused.
+ * @pre The AccessibilityManager has been initialized.
*/
Actor GetCurrentFocusActor();
/**
* @brief Get the focus group of current focused actor.
*
- * @pre The AccessibilityManager has been initialized.
- *
+ * @SINCE_1_0.0
* @return A handle to the immediate parent of the current focused
* actor which is also a focus group, or an empty handle if no actor
* is focused.
+ * @pre The AccessibilityManager has been initialized.
+ *
*/
Actor GetCurrentFocusGroup();
/**
* @brief Get the focus order of currently focused actor.
- * @pre The AccessibilityManager has been initialized.
- *
+ * @SINCE_1_0.0
* @return The focus order of the currently focused actor or 0 if no
* actor is in focus.
+ * @pre The AccessibilityManager has been initialized.
+ *
*/
unsigned int GetCurrentFocusOrder();
* When the focus movement is wrapped around, the focus will be moved
* to the first focusable actor when it reaches the end of the focus chain.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return true if the moving was successful
+ * @pre The AccessibilityManager has been initialized.
*/
bool MoveFocusForward();
* moved to the last focusable actor when it reaches the beginning
* of the focus chain.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return true if the moving was successful
+ * @pre The AccessibilityManager has been initialized.
*/
bool MoveFocusBackward();
* @brief Clear the focus from the current focused actor if any, so
* that no actor is focused in the focus chain.
*
- * It will emit focus changed signal without current focused actor
+ * It will emit focus changed signal without current focused actor.
+ * @SINCE_1_0.0
* @pre The AccessibilityManager has been initialized.
*/
void ClearFocus();
/**
* @brief Clear the every registered focusable actor from focus-manager.
+ * @SINCE_1_0.0
* @pre The AccessibilityManager has been initialized.
*/
void Reset();
* @brief Set whether an actor is a focus group that can limit the
* scope of focus movement to its child actors in the focus chain.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be set as a focus group.
* @param isFocusGroup Whether to set the actor to be a focus group or not.
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
void SetFocusGroup(Actor actor, bool isFocusGroup);
/**
* @brief Check whether the actor is set as a focus group or not.
*
- * @pre The AccessibilityManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be checked.
* @return Whether the actor is set as a focus group.
+ * @pre The AccessibilityManager has been initialized.
+ * @pre The Actor has been initialized.
*/
bool IsFocusGroup(Actor actor) const;
* When the group mode is enabled, the focus movement will be limited to the child actors
* of the current focus group including the current focus group itself. The current focus
* group is the closest ancestor of the current focused actor that set as a focus group.
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @param enabled Whether the group mode is enabled or not
+ * @pre The AccessibilityManager has been initialized.
*/
void SetGroupMode(bool enabled);
/**
* @brief Get whether the group mode is enabled or not.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return Whether the group mode is enabled or not.
+ * @pre The AccessibilityManager has been initialized.
*/
bool GetGroupMode() const;
*
* When both the wrap mode and the group mode are enabled, focus will be
* wrapped within the current focus group. Focus will not be wrapped in default.
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @param wrapped Whether the focus movement is wrapped around or not
+ * @pre The AccessibilityManager has been initialized.
*/
void SetWrapMode(bool wrapped);
/**
* @brief Get whether the wrap mode is enabled or not.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return Whether the wrap mode is enabled or not.
+ * @pre The AccessibilityManager has been initialized.
*/
bool GetWrapMode() const;
* AccessibilityManager and will be added to the focused actor as a
* highlight.
*
+ * @SINCE_1_0.0
+ * @param indicator The indicator actor to be added
* @pre The AccessibilityManager has been initialized.
* @pre The indicator actor has been initialized.
- * @param indicator The indicator actor to be added
*/
void SetFocusIndicatorActor(Actor indicator);
/**
* @brief Get the focus indicator actor.
*
- * @pre The AccessibilityManager has been initialized.
+ * @SINCE_1_0.0
* @return A handle to the focus indicator actor
+ * @pre The AccessibilityManager has been initialized.
*/
Actor GetFocusIndicatorActor();
/**
* @brief Returns the closest ancestor of the given actor that is a focus group.
*
+ * @SINCE_1_0.0
* @param actor The actor to be checked for its focus group
* @return The focus group the given actor belongs to or an empty handle if the given actor doesn't belong to any focus group
*/
/**
* @brief Returns the current position of the read action.
+ * @SINCE_1_0.0
* @return The current event position.
*/
Vector2 GetReadPosition() const;
* @code
* void YourCallbackName(Actor originalFocusedActor, Actor currentFocusedActor);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
FocusChangedSignalType& FocusChangedSignal();
* @code
* void YourCallbackName(Actor currentFocusedActor, FocusOvershotDirection direction);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
FocusOvershotSignalType& FocusOvershotSignal();
* @code
* void YourCallbackName(Actor activatedActor);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
FocusedActorActivatedSignalType& FocusedActorActivatedSignal();
- public: // Accessibility action signals.
+ public: // Accessibility action signals
/**
* @brief This is emitted when accessibility(screen-reader) feature turned on or off.
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& StatusChangedSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionNextSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionPreviousSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionActivateSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionOverSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadNextSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadPreviousSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionUpSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionDownSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionClearFocusSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionBackSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionScrollUpSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionScrollDownSignal();
/**
* @brief This is emitted when accessibility action is received to scroll left to the
- * previous page (by two finger swipe left)
+ * previous page (by two finger swipe left).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionPageLeftSignal();
/**
* @brief This is emitted when accessibility action is received to scroll right to the
- * next page (by two finger swipe right)
+ * next page (by two finger swipe right).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionPageRightSignal();
/**
* @brief This is emitted when accessibility action is received to scroll up to the
- * previous page (by one finger swipe left and right)
+ * previous page (by one finger swipe left and right).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionPageUpSignal();
/**
* @brief This is emitted when accessibility action is received to scroll down to the
- * next page (by one finger swipe right and left)
+ * next page (by one finger swipe right and left).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionPageDownSignal();
/**
* @brief This is emitted when accessibility action is received to move the focus to
- * the first item on the screen (by one finger swipe up and down)
+ * the first item on the screen (by one finger swipe up and down).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionMoveToFirstSignal();
/**
* @brief This is emitted when accessibility action is received to move the focus to
- * the last item on the screen (by one finger swipe down and up)
+ * the last item on the screen (by one finger swipe down and up).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionMoveToLastSignal();
/**
* @brief This is emitted when accessibility action is received to focus and read from the
- * first item on the top continously (by three fingers single tap)
+ * first item on the top continously (by three fingers single tap).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadFromTopSignal();
/**
* @brief This is emitted when accessibility action is received to move the focus to and
- * read from the next item continously (by three fingers double tap)
+ * read from the next item continously (by three fingers double tap).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadFromNextSignal();
/**
* @brief This is emitted when accessibility action is received to zoom (by one finger
- * triple tap)
+ * triple tap).
*
* A callback of the following type may be connected:
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionZoomSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadIndicatorInformationSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionReadPauseResumeSignal();
* @code
* bool YourCallback( AccessibilityManager& manager );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionSignalType& ActionStartStopSignal();
* @code
* bool YourCallback( AccessibilityManager& manager, const TouchEvent& event );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
AccessibilityActionScrollSignalType& ActionScrollSignal();
* @brief Alignment is a container which provides an easy way to align other actors inside its boundary.
*
* Additionaly it provides a scaling property to resize the contained actors @see Scaling.
+ * @SINCE_1_0.0
* @note The use of scaling property will override all constraints applied to actors.
*
* All actors added to an alignment are going to be set with the same anchor point and parent origin. And, if the scaling property is set to a value
public:
/**
* @brief Different types of alignment.
+ * @SINCE_1_0.0
*/
enum Type
{
- HorizontalLeft = 1,
- HorizontalCenter = 2,
- HorizontalRight = 4,
- VerticalTop = 8,
- VerticalCenter = 16,
- VerticalBottom = 32
+ HorizontalLeft = 1, ///< Horizontal left alignment @SINCE_1_0.0
+ HorizontalCenter = 2, ///< Horizontal center alignment @SINCE_1_0.0
+ HorizontalRight = 4, ///< Horizontal right alignment @SINCE_1_0.0
+ VerticalTop = 8, ///< Vertical top alignment @SINCE_1_0.0
+ VerticalCenter = 16, ///< Vertical center alignment @SINCE_1_0.0
+ VerticalBottom = 32 ///< Vertical bottom alignment @SINCE_1_0.0
};
/**
* @brief Scaling determines how actors are scaled, to match the alignment's boundary.
+ * @SINCE_1_0.0
*/
enum Scaling
{
- ScaleNone, ///< The original size is kept.
- ScaleToFill, ///< Scale added actors to fill alignment's boundary. Aspect ratio is not maintained.
- ScaleToFitKeepAspect, ///< Scale added actors to fit within the alignment's boundary. Aspect ratio is maintained.
- ScaleToFillKeepAspect, ///< Scale added actors to fill the alignment's boundary. Aspect ratio is maintained, and the actor may exceed the alignment's boundary.
- ShrinkToFit, ///< If added actors are larger than the alignment's boundary it will be shrunk down to fit. Aspect ratio is not maintained
- ShrinkToFitKeepAspect, ///< If added actors are larger than the alignment's boundary it will be shrunk down to fit. Aspect ratio is maintained
+ ScaleNone, ///< The original size is kept. @SINCE_1_0.0
+ ScaleToFill, ///< Scale added actors to fill alignment's boundary. Aspect ratio is not maintained. @SINCE_1_0.0
+ ScaleToFitKeepAspect, ///< Scale added actors to fit within the alignment's boundary. Aspect ratio is maintained. @SINCE_1_0.0
+ ScaleToFillKeepAspect, ///< Scale added actors to fill the alignment's boundary. Aspect ratio is maintained, and the actor may exceed the alignment's boundary. @SINCE_1_0.0
+ ShrinkToFit, ///< If added actors are larger than the alignment's boundary it will be shrunk down to fit. Aspect ratio is not maintained @SINCE_1_0.0
+ ShrinkToFitKeepAspect, ///< If added actors are larger than the alignment's boundary it will be shrunk down to fit. Aspect ratio is maintained @SINCE_1_0.0
};
/**
* @brief Structure describing the padding values.
+ * @SINCE_1_0.0
*/
struct Padding
{
/**
* @brief Constructor
+ * @SINCE_1_0.0
*/
Padding()
: left( 0.f ),
/**
* @brief Constructor
*
+ * @SINCE_1_0.0
* @param[in] l Left padding
* @param[in] r Right padding
* @param[in] t Top padding
* @brief Create an Alignment handle; this can be initialised with Alignment::New().
*
* Calling member functions with an uninitialised handle is not allowed.
+ * @SINCE_1_0.0
*/
Alignment();
/**
* @brief Creates an alignment control.
*
+ * @SINCE_1_0.0
* @param [in] horizontal Specifies how to align actors horizontally. Could be HorizontalLeft, HorizontalCenter or HorizontalRight. By default HorizontalCenter.
* @param [in] vertical Specifies how to align actors vertically. Could be VerticalTop, VerticalCenter or VerticalBottom. By default VerticalCenter.
* @return A handle to the Alignment control.
/**
* @brief Copy constructor. Creates another handle that points to the same real object.
*
+ * @SINCE_1_0.0
* @param[in] alignment Object to copy.
*/
Alignment(const Alignment& alignment);
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~Alignment();
/**
- * @brief Downcast an Object handle to Alignment.
+ * @brief Downcast a handle to Alignment handle.
*
* If handle points to a Alignment the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a Alignment or an uninitialized handle
+ * @return A handle to a Alignment or an uninitialized handle
*/
static Alignment DownCast( BaseHandle handle );
/**
* @brief Sets the new alignment. By default ( HorizontalCenter | VerticalCenter ).
*
- * @note there should only be one horizontal and one vertical policy
+ * @SINCE_1_0.0
* @param [in] type The new alignment option.
+ * @note There should only be one horizontal and one vertical policy.
*/
void SetAlignmentType( Type type );
* }
* @endcode
*
+ * @SINCE_1_0.0
* @return the alignment value.
*/
Type GetAlignmentType() const;
/**
* @brief Sets how added actors scale to fit the alignment's boundary.
*
- * @see Scaling.
+ * @SINCE_1_0.0
* @param[in] scaling The scaling property.
+ * @see Scaling.
*/
void SetScaling( Scaling scaling );
/**
* @brief Retrieves the scaling property.
*
- * @see Scaling.
+ * @SINCE_1_0.0
* @return The scaling.
+ * @see Scaling.
*/
Scaling GetScaling() const;
/**
* @brief Set a padding value.
*
+ * @SINCE_1_0.0
* @param [in] padding The left, right, top, bottom padding values.
*/
void SetPadding( const Padding& padding );
/**
* @brief Get the padding values.
*
+ * @SINCE_1_0.0
* @return The left, right, top, bottom padding values.
*/
const Padding& GetPadding() const;
* @brief Assignment operator.
*
* Changes this handle to point to another real object.
+ * @SINCE_1_0.0
* @param[in] alignment Object to copy
* @return A reference to this
*/
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL Alignment( Internal::Alignment& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL Alignment( Dali::Internal::CustomActor* internal );
* | %Action Name | %Button method called |
* |------------------|-----------------------------|
* | buttonClick | %DoClickAction() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API Button : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the Button class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- DISABLED = PROPERTY_START_INDEX, ///< name "disabled", @see SetDisabled(), type bool
- AUTO_REPEATING, ///< name "autoRepeating", @see SetAutoRepeating(), type bool
- INITIAL_AUTO_REPEATING_DELAY, ///< name "initialAutoRepeatingDelay", @see SetInitialAutoRepeatingDelay(), type float
- NEXT_AUTO_REPEATING_DELAY, ///< name "nextAutoRepeatingDelay", @see SetNextAutoRepeatingDelay(), type float
- TOGGLABLE, ///< name "togglable", @see SetTogglableButton(), type bool
- SELECTED, ///< name "selected", @see SetSelected(), type bool
- UNSELECTED_STATE_IMAGE, ///< name "unselectedStateImage", @see SetUnselectedImage(), type std::string
- SELECTED_STATE_IMAGE, ///< name "selectedStateImage", @see SetSelectedImage(), type std::string
- DISABLED_STATE_IMAGE, ///< name "disabledStateImage", @see SetDisabledImage(), type std::string
- UNSELECTED_COLOR, ///< name "unselectedColor", type Vector4
- SELECTED_COLOR, ///< name "selectedColor", type Vector4
- LABEL, ///< name "label", type Property::Map
+ DISABLED = PROPERTY_START_INDEX, ///< name "disabled", @see SetDisabled(), type bool @SINCE_1_0.0
+ AUTO_REPEATING, ///< name "autoRepeating", @see SetAutoRepeating(), type bool @SINCE_1_0.0
+ INITIAL_AUTO_REPEATING_DELAY, ///< name "initialAutoRepeatingDelay", @see SetInitialAutoRepeatingDelay(), type float @SINCE_1_0.0
+ NEXT_AUTO_REPEATING_DELAY, ///< name "nextAutoRepeatingDelay", @see SetNextAutoRepeatingDelay(), type float @SINCE_1_0.0
+ TOGGLABLE, ///< name "togglable", @see SetTogglableButton(), type bool @SINCE_1_0.0
+ SELECTED, ///< name "selected", @see SetSelected(), type bool @SINCE_1_0.0
+ UNSELECTED_STATE_IMAGE, ///< name "unselectedStateImage", @see SetUnselectedImage(), type std::string @SINCE_1_0.0
+ SELECTED_STATE_IMAGE, ///< name "selectedStateImage", @see SetSelectedImage(), type std::string @SINCE_1_0.0
+ DISABLED_STATE_IMAGE, ///< name "disabledStateImage", @see SetDisabledImage(), type std::string @SINCE_1_0.0
+ UNSELECTED_COLOR, ///< name "unselectedColor", type Vector4 @SINCE_1_0.0
+ SELECTED_COLOR, ///< name "selectedColor", type Vector4 @SINCE_1_0.0
+ LABEL, ///< name "label", type Property::Map @SINCE_1_0.0
// Deprecated properties:
- LABEL_TEXT, ///< name "labelText", @see SetLabelText(), type std::string
+ LABEL_TEXT, ///< name "labelText", @see SetLabelText(), type std::string @SINCE_1_0.0
};
};
*
* Only derived versions can be instantiated. Calling member
* functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
Button();
/**
* @brief Copy constructor.
+ * @SINCE_1_0.0
*/
Button( const Button& button );
/**
* @brief Assignment operator.
+ * @SINCE_1_0.0
*/
Button& operator=( const Button& button );
/**
- * @brief Downcast an Object handle to Button.
+ * @brief Downcast a handle to Button handle.
*
* If handle points to a Button the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a Button or an uninitialized handle
+ * @return A handle to a Button or an uninitialized handle
*/
static Button DownCast( BaseHandle handle );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~Button();
*
* No signals are emitted when the \e disabled property is set.
*
+ * @SINCE_1_0.0
* @param[in] disabled property.
*/
void SetDisabled( bool disabled );
/**
+ * @brief Returns if the button is disabled.
+ * @SINCE_1_0.0
* @return \e true if the button is \e disabled.
*/
bool IsDisabled() const;
* If the \e autorepeating property is set to \e true, then the \e togglable property is set to false
* but no signal is emitted.
*
+ * @SINCE_1_0.0
* @param[in] autoRepeating \e autorepeating property.
*/
void SetAutoRepeating( bool autoRepeating );
/**
+ * @brief Returns if the autorepeating property is set.
+ * @SINCE_1_0.0
* @return \e true if the \e autorepeating property is set.
*/
bool IsAutoRepeating() const;
*
* By default this value is set to 0.15 seconds.
*
- * @pre initialAutoRepeatingDelay must be greater than zero.
+ * @SINCE_1_0.0
* @param[in] initialAutoRepeatingDelay in seconds.
+ * @pre initialAutoRepeatingDelay must be greater than zero.
*/
void SetInitialAutoRepeatingDelay( float initialAutoRepeatingDelay );
/**
+ * @brief Gets the initial autorepeating delay in seconds.
+ * @SINCE_1_0.0
* @return the initial autorepeating delay in seconds.
*/
float GetInitialAutoRepeatingDelay() const;
*
* By default this value is set to 0.05 seconds.
*
- * @pre nextAutoRepeatingDelay must be greater than zero.
+ * @SINCE_1_0.0
* @param[in] nextAutoRepeatingDelay in seconds.
+ * @pre nextAutoRepeatingDelay must be greater than zero.
*/
void SetNextAutoRepeatingDelay( float nextAutoRepeatingDelay );
/**
+ * @brief Gets the next autorepeating delay in seconds.
+ * @SINCE_1_0.0
* @return the next autorepeating delay in seconds.
*/
float GetNextAutoRepeatingDelay() const;
*
* If the \e togglable property is set to \e true, then the \e autorepeating property is set to false.
*
+ * @SINCE_1_0.0
* @param[in] togglable property.
*/
void SetTogglableButton( bool togglable );
/**
+ * @brief Returns if the togglable property is set.
+ * @SINCE_1_0.0
* @return \e true if the \e togglable property is set.
*/
bool IsTogglableButton() const;
/**
- * Sets the button as selected or unselected.
+ * @brief Sets the button as selected or unselected.
*
* \e togglable property must be set to \e true.
*
* Emits a Button::StateChangedSignal() signal.
*
+ * @SINCE_1_0.0
* @param[in] selected property.
*/
void SetSelected( bool selected );
/**
- * @return \e true if the \e selected property is set and the button is togglable.
+ * @brief Returns if the selected property is set and the button is togglable.
+ * @SINCE_1_0.0
+ * @return \e true if the button is \e selected.
*/
bool IsSelected() const;
/**
* @brief Sets the animation time.
*
+ * @SINCE_1_0.0
* @param[in] animationTime The animation time in seconds.
*/
void SetAnimationTime( float animationTime );
/**
* @brief Retrieves button's animation time.
*
+ * @SINCE_1_0.0
* @return The animation time in seconds.
*/
float GetAnimationTime() const;
/**
* @brief Sets the button's label.
*
+ * @SINCE_1_0.0
* @param[in] label The label text.
*/
void SetLabelText( const std::string& label );
/**
* @brief Gets the label.
*
+ * @SINCE_1_0.0
* @return The label text.
*/
std::string GetLabelText() const;
/**
* @brief Sets the unselected button image.
*
+ * @SINCE_1_0.0
* @param[in] filename The button image.
*/
void SetUnselectedImage( const std::string& filename );
/**
* @brief Sets the background image.
*
+ * @SINCE_1_0.0
* @param[in] filename The background image.
*/
void SetBackgroundImage( const std::string& filename );
/**
* @brief Sets the selected image.
*
+ * @SINCE_1_0.0
* @param[in] filename The selected image.
*/
void SetSelectedImage( const std::string& filename );
/**
* @brief Sets the selected background image.
*
+ * @SINCE_1_0.0
* @param[in] filename The selected background image.
*/
void SetSelectedBackgroundImage( const std::string& filename );
/**
* @brief Sets the disabled background image.
*
+ * @SINCE_1_0.0
* @param[in] filename The disabled background image.
*/
void SetDisabledBackgroundImage( const std::string& filename );
/**
* @brief Sets the disabled button image.
*
+ * @SINCE_1_0.0
* @param[in] filename The disabled button image.
*/
void SetDisabledImage( const std::string& filename );
/**
* @brief Sets the disabled selected button image.
*
+ * @SINCE_1_0.0
* @param[in] filename The disabled selected button image.
*/
void SetDisabledSelectedImage( const std::string& filename );
// Deprecated API
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use SetLabelText.
*
* @brief Sets the label with an actor.
*
+ * @SINCE_1_0.0
* @param[in] label The actor to use as a label
*/
void SetLabel( Actor label );
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use SetUnselectedImage.
*
* @brief Sets the button image.
*
+ * @SINCE_1_0.0
* @param[in] image The button image.
*/
void SetButtonImage( Image image );
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use SetSelectedImage( const std::string& filename ).
*
* @brief Sets the selected image.
*
+ * @SINCE_1_0.0
* @param[in] image The selected image.
*/
void SetSelectedImage( Image image );
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50
*
* @brief Gets the button image.
*
+ * @SINCE_1_0.0
+ * @remarks Avoid using this method as it's a legacy code.
* @return An actor with the button image.
*/
Actor GetButtonImage() const;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50
*
* @brief Gets the selected image.
*
+ * @SINCE_1_0.0
+ * @remarks Avoid using this method as it's a legacy code.
* @return An actor with the selected image.
*/
Actor GetSelectedImage() const;
/**
* @brief Button signal type
+ * @SINCE_1_0.0
*/
typedef Signal< bool ( Button ) > ButtonSignalType;
* @code
* bool YourCallbackName( Button button );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
ButtonSignalType& PressedSignal();
* @code
* bool YourCallbackName( Button button );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
ButtonSignalType& ReleasedSignal();
* @code
* bool YourCallbackName( Button button );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
ButtonSignalType& ClickedSignal();
/**
* @brief This signal is emitted when the button's state is changed.
+ *
* The application can get the state by calling IsSelected().
*
* A callback of the following type may be connected:
* @code
* bool YourCallbackName( Button button );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
ButtonSignalType& StateChangedSignal();
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL Button( Internal::Button& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL Button( Dali::Internal::CustomActor* internal );
*/
/**
- * CheckBoxButton provides a check box button which user can check or uncheck.
+ * @brief CheckBoxButton provides a check box button which user can check or uncheck.
*
* By default a CheckBoxButton emits a Button::ClickedSignal() signal when the button changes its state to selected or unselected.
*
- * The button's appearance could be modified by setting images or actors with CheckBoxButton::SetBackgroundImage,
- * CheckBoxButton::SetSelectedImage, CheckBoxButton::SetDisabledBackgroundImage and CheckBoxButton::SetDisabledSelectedImage.
+ * The button's appearance could be modified by Button::SetUnselectedImage, Button::SetBackgroundImage,
+ * Button::SetSelectedImage, Button::SetSelectedBackgroundImage, Button::SetDisabledBackgroundImage,
+ * Button::SetDisabledImage, and Button::SetDisabledSelectedImage.
*
* When the button is not disabled, if it's not selected it only shows the \e background image. The \e selected image is shown over the
* \e background image when the box is selected (\e background image is not replaced by \e selected image).
*
* When the button is disabled, \e background image and \e selected image are replaced by \e disabled images.
*
- * CheckBoxButton doesn't have a text. However, a Dali::Toolkit::TableView with a Dali::TextActor or a Dali::Toolkit::TextView
- * and a CheckBoxButton could be used instead.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API CheckBoxButton : public Button
{
public:
/**
- * Create an uninitialized CheckBoxButton; this can be initialized with CheckBoxButton::New()
+ * @brief Create an uninitialized CheckBoxButton; this can be initialized with CheckBoxButton::New().
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
CheckBoxButton();
/**
- * Copy constructor.
+ * @brief Copy constructor.
+ * @SINCE_1_0.0
*/
CheckBoxButton( const CheckBoxButton& checkBox );
/**
- * Assignment operator.
+ * @brief Assignment operator.
+ * @SINCE_1_0.0
*/
CheckBoxButton& operator=( const CheckBoxButton& checkBox );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~CheckBoxButton();
/**
- * Create an initialized CheckBoxButton.
+ * @brief Create an initialized CheckBoxButton.
+ * @SINCE_1_0.0
* @return A handle to a newly allocated Dali resource.
*/
static CheckBoxButton New();
/**
- * Downcast an Object handle to CheckBoxButton. If handle points to a CheckBoxButton the
+ * @brief Downcast a handle to CheckBoxButton handle.
+ *
+ * If handle points to a CheckBoxButton the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a CheckBoxButton or an uninitialized handle
*/
public: // Not intended for application developers
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL CheckBoxButton( Internal::CheckBoxButton& implementation );
/**
- * Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL CheckBoxButton( Dali::Internal::CustomActor* internal );
* and a Button::ReleasedSignal() signal when it's released or having pressed it, the touch point leaves the boundary of the button.
*
* See Button for more detail on signals and modifying appearance via properties.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API PushButton : public Button
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Button::PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserving 1000 property indices
+ PROPERTY_START_INDEX = Button::PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserving 1000 property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the PushButton class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- UNSELECTED_ICON = PROPERTY_START_INDEX, ///< Property, name "unselectedIcon", type std::string
- SELECTED_ICON, ///< Property, name "selectedIcon", type std::string
- ICON_ALIGNMENT, ///< Property, name "iconAlignment", type std::string
- LABEL_PADDING, ///< Property, name "labelPadding", type Vector4
- ICON_PADDING, ///< Property, name "iconPadding", type Vector4
+ UNSELECTED_ICON = PROPERTY_START_INDEX, ///< Property, name "unselectedIcon", type std::string @SINCE_1_0.0
+ SELECTED_ICON, ///< Property, name "selectedIcon", type std::string @SINCE_1_0.0
+ ICON_ALIGNMENT, ///< Property, name "iconAlignment", type std::string @SINCE_1_0.0
+ LABEL_PADDING, ///< Property, name "labelPadding", type Vector4 @SINCE_1_0.0
+ ICON_PADDING, ///< Property, name "iconPadding", type Vector4 @SINCE_1_0.0
};
};
* @brief Create an uninitialized PushButton; this can be initialized with PushButton::New().
*
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
PushButton();
/**
* @brief Copy constructor.
+ * @SINCE_1_0.0
*/
PushButton( const PushButton& pushButton );
/**
* @brief Assignment operator.
+ * @SINCE_1_0.0
*/
PushButton& operator=( const PushButton& pushButton );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~PushButton();
/**
* @brief Create an initialized PushButton.
*
+ * @SINCE_1_0.0
* @return A handle to a newly allocated Dali resource.
*/
static PushButton New();
/**
- * @brief Downcast an Object handle to PushButton.
+ * @brief Downcast a handle to PushButton handle.
*
* If handle points to a PushButton the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a PushButton or an uninitialized handle
*/
using Button::SetButtonImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetUnselectedImage.
*
* @brief Sets the unselected image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetButtonImage( Actor image );
using Button::SetBackgroundImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetBackgroundImage.
*
* @brief Sets the background image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetBackgroundImage( Actor image );
using Button::SetSelectedImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetSelectedImage( const std::string& filename ).
*
* @brief Sets the selected image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetSelectedImage( Actor image );
using Button::SetSelectedBackgroundImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetSelectedBackgroundImage.
*
* @brief Sets the selected background image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetSelectedBackgroundImage( Actor image );
using Button::SetDisabledBackgroundImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetDisabledBackgroundImage.
*
* @brief Sets the disabled background image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetDisabledBackgroundImage( Actor image );
using Button::SetDisabledImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetDisabledImage.
*
* @brief Sets the disabled image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetDisabledImage( Actor image );
using Button::SetDisabledSelectedImage;
/**
- * @deprecated DALi 1.0.50
+ * @DEPRECATED_1_0.50. Instead, use Button::SetDisabledSelectedImage.
*
* @brief Sets the disabled selected image with an Actor.
*
+ * @SINCE_1_0.0
* @param[in] image The Actor to use.
*/
void SetDisabledSelectedImage( Actor image );
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL PushButton( Internal::PushButton& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL PushButton( Dali::Internal::CustomActor* internal );
*
* Radio buttons are designed to select one of many option at the same time.
*
- * Every button have its own \e label and \e state, which can be modified by RadioButton::SetLabel and Button::SetSelected.
+ * Every button have its own \e label and \e state, which can be modified by Button::SetLabelText and Button::SetSelected.
*
* RadioButton can change its current state using Button::SetSelected.
*
* When \e selected RadioButton is set to \e unselected no other RadioButtons in his group is set to \e selected.
*
* A Button::StateChangedSignal() is emitted when the RadioButton change its state to \e selected or \e unselected.
+ *
+ * Usage example: -
+ *
+ * @code
+ * // in Creating a DALi Application
+ *
+ * // Create a group to bind two or more RadioButtons together
+ * Actor radioGroup = Actor::New();
+ * radioGroup.SetParentOrigin( ParentOrigin::CENTER );
+ * Stage::GetCurrent().Add( radioGroup );
+ *
+ * // Make the first RadioButton and add it to its parent
+ * RadioButton button1 = RadioButton::New();
+ * button1.SetLabelText( "button1" );
+ * button1.SetBackgroundColor( Color::WHITE );
+ * button1.SetPosition( 0, -40 );
+ * radioGroup.Add( button1 );
+ *
+ * // Make more RadioButtons and add them to their parent
+ * RadioButton button2 = RadioButton::New();
+ * button2.SetLabelText( "button2" );
+ * button2.SetBackgroundColor( Color::WHITE );
+ * button2.SetPosition( 0, 40 );
+ * radioGroup.Add( button2 );
+ *
+ * @endcode
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API RadioButton: public Button
{
* @brief Create an uninitialized RadioButton; this can be initialized with RadioButton::New().
*
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
RadioButton();
/**
* @brief Copy constructor.
+ * @SINCE_1_0.0
*/
RadioButton( const RadioButton& radioButton );
/**
* @brief Assignment operator.
+ * @SINCE_1_0.0
*/
RadioButton& operator=( const RadioButton& radioButton );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~RadioButton();
/**
* @brief Create an initialized RadioButton.
*
+ * @SINCE_1_0.0
* @return A handle to a newly allocated Dali resource.
*/
static RadioButton New();
/**
* @brief Create an initialized RadioButton with given label.
*
+ * @SINCE_1_0.0
* @param[in] label The button label.
*
* @return A handle to a newly allocated Dali resource.
static RadioButton New( const std::string& label );
/**
- * @brief Downcast an Object handle to RadioButton.
+ * @brief Downcast a handle to RadioButton handle.
*
* If handle points to a RadioButton the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a RadioButton or an uninitialized handle
+ * @return A handle to a RadioButton or an uninitialized handle
*/
static RadioButton DownCast( BaseHandle handle );
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL RadioButton( Internal::RadioButton& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL RadioButton( Dali::Internal::CustomActor* internal );
+++ /dev/null
-#ifndef __DALI_TOOLKIT_CONTROL_DEPTH_INDEX_RANGES_H__
-#define __DALI_TOOLKIT_CONTROL_DEPTH_INDEX_RANGES_H__
-
-/*
- * Copyright (c) 2016 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 INCLUDES
-#include <dali/public-api/actors/layer.h>
-
-namespace Dali
-{
-namespace Toolkit
-{
-/**
- * @addtogroup dali_toolkit_controls
- * @{
- */
-
-/**
- * @deprecated DALi 1.1.16
- *
- * @brief These depth indices should not be used.
- */
-enum DepthIndexRanges
-{
- BACKGROUND_DEPTH_INDEX = static_cast<int>( -Dali::Layer::TREE_DEPTH_MULTIPLIER * 0.1f ), ///< @deprecated DALi 1.1.16
- CONTENT_DEPTH_INDEX = 0, ///< @deprecated DALi 1.1.16
- DECORATION_DEPTH_INDEX = static_cast<int>( Dali::Layer::TREE_DEPTH_MULTIPLIER * 0.1f ) ///< @deprecated DALi 1.1.16
-};
-
-/**
- * @}
- */
-}
-
-}
-
-#endif
* It will provide some common functionality required by all controls.
* Implements ConnectionTrackerInterface so that signals (typically connected to member functions) will
* be disconnected automatically when the control is destroyed.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API Control : public CustomActorImpl, public ConnectionTrackerInterface
{
* @brief Create a new ControlImpl instance that does not require touch by default.
*
* If touch is required then the user can connect to this class' touch signal.
+ * @SINCE_1_0.0
* @return A handle to the ControlImpl instance.
*/
static Toolkit::Control New();
/**
* @brief Virtual destructor.
+ * @SINCE_1_0.0
*/
virtual ~Control();
/**
* @brief Set the background with a property map.
*
+ * @SINCE_1_0.0
* @param[in] map The background property map.
*/
void SetBackground(const Property::Map& map);
* @code
* EnableGestureDetection(Gesture::Type(Gesture::Pinch | Gesture::Tap | Gesture::Pan));
* @endcode
+ * @SINCE_1_0.0
* @param[in] type The gesture type(s) to enable.
*/
void EnableGestureDetection( Gesture::Type type );
* @brief Allows deriving classes to disable any of the gesture detectors.
*
* Like EnableGestureDetection, this can also be called using bitwise or.
+ * @SINCE_1_0.0
* @param[in] type The gesture type(s) to disable.
* @see EnableGetureDetection
*/
* detection then they can access the gesture detector through this
* API and modify the detection.
*
+ * @SINCE_1_0.0
* @return The pinch gesture detector.
* @pre Pinch detection should have been enabled via EnableGestureDetection().
* @see EnableGestureDetection
* detection then they can access the gesture detector through this
* API and modify the detection.
*
+ * @SINCE_1_0.0
* @return The pan gesture detector.
* @pre Pan detection should have been enabled via EnableGestureDetection().
* @see EnableGestureDetection
* detection then they can access the gesture detector through this
* API and modify the detection.
*
+ * @SINCE_1_0.0
* @return The tap gesture detector.
* @pre Tap detection should have been enabled via EnableGestureDetection().
* @see EnableGestureDetection
* detection then they can access the gesture detector through this
* API and modify the detection.
*
+ * @SINCE_1_0.0
* @return The long press gesture detector.
* @pre Long press detection should have been enabled via EnableGestureDetection().
* @see EnableGestureDetection
* keyboard focus movement between its child actors).
*
* The control doesn't support it by default.
+ * @SINCE_1_0.0
* @param[in] isSupported Whether this control supports two dimensional keyboard navigation.
*/
void SetKeyboardNavigationSupport( bool isSupported );
/**
* @brief Gets whether this control supports two dimensional keyboard navigation.
*
+ * @SINCE_1_0.0
* @return true if this control supports two dimensional keyboard navigation.
*/
bool IsKeyboardNavigationSupported();
*
* (i.e. the scope of keyboard focus movement
* can be limitied to its child actors). The control is not a focus group by default.
+ * @SINCE_1_0.0
* @param[in] isFocusGroup Whether this control is set as a focus group for keyboard navigation.
*/
void SetAsKeyboardFocusGroup( bool isFocusGroup );
/**
* @brief Gets whether this control is a focus group for keyboard navigation.
*
+ * @SINCE_1_0.0
* @return true if this control is set as a focus group for keyboard navigation.
*/
bool IsKeyboardFocusGroup();
/**
* @brief Called by the AccessibilityManager to activate the Control.
+ * @SINCE_1_0.0
*/
DALI_INTERNAL void AccessibilityActivate();
/**
* @brief Called by the KeyboardFocusManager.
+ * @SINCE_1_0.0
*/
DALI_INTERNAL void KeyboardEnter();
/**
* @brief Called by the KeyInputFocusManager to emit key event signals.
*
+ * @SINCE_1_0.0
* @param[in] event The key event.
* @return True if the event was consumed.
*/
*
* Should be called last by the control after it acts on the Input Focus change.
*
+ * @SINCE_1_0.0
* @param[in] focusGained True if gained, False if lost
*/
void EmitKeyInputFocusSignal( bool focusGained );
// Flags for the constructor
enum ControlBehaviour
{
- REQUIRES_STYLE_CHANGE_SIGNALS = 1 << ( CustomActorImpl::ACTOR_FLAG_COUNT + 0 ), ///< True if needs to monitor style change signals such as theme/font change
- REQUIRES_KEYBOARD_NAVIGATION_SUPPORT = 1 << ( CustomActorImpl::ACTOR_FLAG_COUNT + 1 ), ///< True if needs to support keyboard navigation
+ REQUIRES_STYLE_CHANGE_SIGNALS = 1 << ( CustomActorImpl::ACTOR_FLAG_COUNT + 0 ), ///< True if needs to monitor style change signals such as theme/font change @SINCE_1_0.0
+ REQUIRES_KEYBOARD_NAVIGATION_SUPPORT = 1 << ( CustomActorImpl::ACTOR_FLAG_COUNT + 1 ), ///< True if needs to support keyboard navigation @SINCE_1_0.0
LAST_CONTROL_BEHAVIOUR_FLAG
};
/**
* @brief Control constructor
*
+ * @SINCE_1_0.0
* @param[in] behaviourFlags Behavioural flags from ControlBehaviour enum
*/
Control( ControlBehaviour behaviourFlags );
/**
* @brief Second phase initialization.
+ * @SINCE_1_0.0
*/
void Initialize();
* @brief This method is called after the Control has been initialized.
*
* Derived classes should do any second phase initialization by overriding this method.
+ * @SINCE_1_0.0
*/
virtual void OnInitialize();
*
* Could be overridden by derived classes.
*
+ * @SINCE_1_0.0
* @param[in] child The added actor.
*/
virtual void OnControlChildAdd( Actor& child );
*
* Could be overridden by derived classes.
*
+ * @SINCE_1_0.0
* @param[in] child The removed actor.
*/
virtual void OnControlChildRemove( Actor& child );
/**
* @brief This method should be overridden by deriving classes requiring notifications when the style changes.
*
+ * @SINCE_1_0.0
* @param[in] styleManager The StyleManager object.
* @param[in] change Information denoting what has changed.
*/
* @brief This method is called when the control is accessibility activated.
*
* Derived classes should override this to perform custom accessibility activation.
+ * @SINCE_1_0.0
* @return true if this control can perform accessibility activation.
*/
virtual bool OnAccessibilityActivated();
* @brief This method should be overridden by deriving classes when they wish to respond the accessibility
* pan gesture.
*
+ * @SINCE_1_0.0
* @param[in] gesture The pan gesture.
* @return true if the pan gesture has been consumed by this control
*/
* @brief This method should be overridden by deriving classes when they wish to respond the accessibility
* touch event.
*
+ * @SINCE_1_0.0
* @param[in] touchEvent The touch event.
* @return true if the touch event has been consumed by this control
*/
* @brief This method should be overridden by deriving classes when they wish to respond
* the accessibility up and down action (i.e. value change of slider control).
*
+ * @SINCE_1_0.0
* @param[in] isIncrease Whether the value should be increased or decreased
* @return true if the value changed action has been consumed by this control
*/
/**
* @brief This method should be overridden by deriving classes when they wish to respond
- * the accessibility zoom action
+ * the accessibility zoom action.
*
+ * @SINCE_1_0.0
* @return true if the zoom action has been consumed by this control
*/
virtual bool OnAccessibilityZoom();
* @brief Called when the control gains key input focus.
*
* Should be overridden by derived classes if they need to customize what happens when focus is gained.
+ * @SINCE_1_0.0
*/
virtual void OnKeyInputFocusGained();
* @brief Called when the control loses key input focus.
*
* Should be overridden by derived classes if they need to customize what happens when focus is lost.
+ * @SINCE_1_0.0
*/
virtual void OnKeyInputFocusLost();
* @brief Gets the next keyboard focusable actor in this control towards the given direction.
*
* A control needs to override this function in order to support two dimensional keyboard navigation.
+ * @SINCE_1_0.0
* @param[in] currentFocusedActor The current focused actor.
* @param[in] direction The direction to move the focus towards.
* @param[in] loopEnabled Whether the focus movement should be looped within the control.
* This allows the application to preform any actions if wishes
* before the focus is actually moved to the chosen actor.
*
+ * @SINCE_1_0.0
* @param[in] commitedFocusableActor The commited focusable actor.
*/
virtual void OnKeyboardFocusChangeCommitted( Actor commitedFocusableActor );
* @brief This method is called when the control has enter pressed on it.
*
* Derived classes should override this to perform custom actions.
+ * @SINCE_1_0.0
* @return true if this control supported this action.
*/
virtual bool OnKeyboardEnter();
* is enabled. The default behaviour is to scale the control by the
* pinch scale.
*
+ * @SINCE_1_0.0
+ * @param[in] pinch The pinch gesture.
* @note If overridden, then the default behaviour will not occur.
* @note Pinch detection should be enabled via EnableGestureDetection().
- * @param[in] pinch The pinch gesture.
* @see EnableGestureDetection
*/
virtual void OnPinch( const PinchGesture& pinch );
* This should be overridden by deriving classes when pan detection
* is enabled.
*
+ * @SINCE_1_0.0
+ * @param[in] pan The pan gesture.
* @note There is no default behaviour with panning.
* @note Pan detection should be enabled via EnableGestureDetection().
- * @param[in] pan The pan gesture.
* @see EnableGestureDetection
*/
virtual void OnPan( const PanGesture& pan );
* This should be overridden by deriving classes when tap detection
* is enabled.
*
+ * @SINCE_1_0.0
+ * @param[in] tap The tap gesture.
* @note There is no default behaviour with a tap.
* @note Tap detection should be enabled via EnableGestureDetection().
- * @param[in] tap The tap gesture.
* @see EnableGestureDetection
*/
virtual void OnTap( const TapGesture& tap );
* This should be overridden by deriving classes when long press
* detection is enabled.
*
+ * @SINCE_1_0.0
+ * @param[in] longPress The long press gesture.
* @note There is no default behaviour associated with a long press.
* @note Long press detection should be enabled via EnableGestureDetection().
- * @param[in] longPress The long press gesture.
* @see EnableGestureDetection
*/
virtual void OnLongPress( const LongPressGesture& longPress );
virtual void SignalDisconnected( SlotObserver* slotObserver, CallbackBase* callback );
/**
- * Retrieve the extension for this control
+ * @brief Retrieve the extension for this control
*
+ * @SINCE_1_0.0
* @return The extension if available, NULL otherwise
*/
virtual Extension* GetControlExtension()
};
/**
- * @brief Get implementation from the handle
+ * @brief Get implementation from the handle.
*
- * @pre handle is initialized and points to a control
+ * @SINCE_1_0.0
* @param handle
* @return implementation
+ * @pre handle is initialized and points to a control
*/
DALI_IMPORT_API Internal::Control& GetImplementation( Dali::Toolkit::Control& handle );
/**
- * @brief Get implementation from the handle
+ * @brief Get implementation from the handle.
*
- * @pre handle is initialized and points to a control
+ * @SINCE_1_0.0
* @param handle
* @return implementation
+ * @pre handle is initialized and points to a control
*/
DALI_IMPORT_API const Internal::Control& GetImplementation( const Dali::Toolkit::Control& handle );
* @brief Control is the base class for all controls.
*
* The implementation of the control must be supplied; see Internal::Control for more details.
+ * @SINCE_1_0.0
* @see Internal::Control
*
* Signals
/**
* @brief The start and end property ranges for control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = PROPERTY_REGISTRATION_START_INDEX, ///< Start index is used by the property registration macro.
- CONTROL_PROPERTY_START_INDEX = PROPERTY_START_INDEX, ///< Start index of Control properties.
- CONTROL_PROPERTY_END_INDEX = CONTROL_PROPERTY_START_INDEX + 1000 ///< Reserving 1000 property indices.
+ PROPERTY_START_INDEX = PROPERTY_REGISTRATION_START_INDEX, ///< Start index is used by the property registration macro. @SINCE_1_0.0
+ CONTROL_PROPERTY_START_INDEX = PROPERTY_START_INDEX, ///< Start index of Control properties. @SINCE_1_0.0
+ CONTROL_PROPERTY_END_INDEX = CONTROL_PROPERTY_START_INDEX + 1000 ///< Reserving 1000 property indices. @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the Control class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- STYLE_NAME = PROPERTY_START_INDEX, ///< name "styleName", @see SetStyleName, type std::string
- BACKGROUND_COLOR, ///< name "background-color", @deprecated DALi 1.1.3 mutually exclusive with BACKGROUND_IMAGE & BACKGROUND, type Vector4
- BACKGROUND_IMAGE, ///< name "background-image", @deprecated DALi 1.1.3 mutually exclusive with BACKGROUND_COLOR & BACKGROUND, type Map
- KEY_INPUT_FOCUS, ///< name "keyInputFocus", @see SetKeyInputFocus, type bool
- BACKGROUND, ///< name "background", @since DALi 1.1.3 mutually exclusive with BACKGROUND_COLOR & BACKGROUND_IMAGE, type Map
+ /**
+ * @brief name "styleName", type std::string
+ * @SINCE_1_0.0
+ * @see SetStyleName
+ */
+ STYLE_NAME = PROPERTY_START_INDEX,
+ /**
+ * @DEPRECATED_1_1.3
+ * @brief name "background-color", mutually exclusive with BACKGROUND_IMAGE & BACKGROUND, type Vector4
+ * @SINCE_1_0.0
+ * @see SetStyleName
+ */
+ BACKGROUND_COLOR,
+ /**
+ * @DEPRECATED_1_1.3
+ * @brief name "background-image", mutually exclusive with BACKGROUND_COLOR & BACKGROUND, type Map
+ * @SINCE_1_0.0
+ */
+ BACKGROUND_IMAGE,
+ /**
+ * @brief name "keyInputFocus", type bool
+ * @SINCE_1_0.0
+ * @see SetKeyInputFocus
+ */
+ KEY_INPUT_FOCUS,
+ /**
+ * @brief name "background", mutually exclusive with BACKGROUND_COLOR & BACKGROUND_IMAGE, type Map
+ * @SINCE_1_1.3
+ */
+ BACKGROUND,
};
};
/**
* @brief Describes the direction to move the keyboard focus towards.
+ * @SINCE_1_0.0
*/
struct KeyboardFocus
{
enum Direction
{
- LEFT, ///< Move keyboard focus towards the left direction
- RIGHT, ///< Move keyboard focus towards the right direction
- UP, ///< Move keyboard focus towards the up direction
- DOWN ///< Move keyboard focus towards the down direction
+ LEFT, ///< Move keyboard focus towards the left direction @SINCE_1_0.0
+ RIGHT, ///< Move keyboard focus towards the right direction @SINCE_1_0.0
+ UP, ///< Move keyboard focus towards the up direction @SINCE_1_0.0
+ DOWN ///< Move keyboard focus towards the down direction @SINCE_1_0.0
};
};
/**
* @brief Create a new instance of a Control.
*
+ * @SINCE_1_0.0
* @return A handle to a new Control.
*/
static Control New();
*
* Only derived versions can be instantiated. Calling member
* functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
Control();
/**
* @brief Copy constructor.
*
- * Creates another handle that points to the same real object
+ * Creates another handle that points to the same real object.
+ * @SINCE_1_0.0
* @param[in] uiControl Handle to copy
*/
Control(const Control& uiControl);
/**
- * @brief Dali::Control is intended as a base class
+ * @brief Dali::Control is intended as a base class.
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~Control();
/**
* @brief Assignment operator.
*
- * Changes this handle to point to another real object
+ * Changes this handle to point to another real object.
+ * @SINCE_1_0.0
* @param[in] handle Object to assign this to
* @return reference to this
*/
public:
/**
- * @brief Downcast an Object handle to Control.
+ * @brief Downcast a handle to Control handle.
*
* If handle points to a Control the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a Control or an uninitialized handle
+ * @return A handle to a Control or an uninitialized handle
*/
static Control DownCast( BaseHandle handle );
* @brief This sets the control to receive key events.
*
* The key event can originate from a virtual or physical keyboard.
+ * @SINCE_1_0.0
* @pre The Control has been initialized.
* @pre The Control should be on the stage before setting keyboard focus.
- * @return True if the control has foucs, False otherwise.
*/
void SetKeyInputFocus();
/**
* @brief Quries whether the control has key input focus.
*
- * Note: The control can be set to have the focus and still not receive all the key events if another control has over ridden it.
+ * @SINCE_1_0.0
+ * @return true if this control has keyboard input focus
+ * @pre The Control has been initialized.
+ * @pre The Control should be on the stage before setting keyboard focus.
+ * @note The control can be set to have the focus and still not receive all the key events if another control has over ridden it.
* As the key input focus mechanism works like a stack, the top most control receives all the key events, and passes on the
* unhandled events to the controls below in the stack. A control in the stack will regain key input focus when there are no more
* controls above it in the focus stack.
- * To query for the conrol which is on top of the focus stack use Dali::Toolkit::KeyInputFocusManager::GetCurrentKeyboardFocusActor()
- * @pre The Control has been initialized.
- * @pre The Control should be on the stage before setting keyboard focus.
- * @return true if this control has keyboard input focus
+ * To query for the conrol which is on top of the focus stack use Dali::Toolkit::KeyInputFocusManager::GetCurrentKeyboardFocusActor().
*/
bool HasKeyInputFocus();
* @brief Once an actor is Set to receive key input focus this function is called to stop it receiving key events.
*
* A check is performed to ensure it was previously set, if this check fails then nothing is done.
+ * @SINCE_1_0.0
* @pre The Actor has been initialized.
*/
void ClearKeyInputFocus();
/**
* @brief Retrieves the pinch gesture detector of the control.
*
+ * @SINCE_1_0.0
* @return The pinch gesture detector.
* @note Will return an empty handle if the control does not handle the gesture itself.
*/
/**
* @brief Retrieves the pan gesture detector of the control.
*
+ * @SINCE_1_0.0
* @return The pan gesture detector.
* @note Will return an empty handle if the control does not handle the gesture itself.
*/
/**
* @brief Retrieves the tap gesture detector of the control.
*
+ * @SINCE_1_0.0
* @return The tap gesture detector.
* @note Will return an empty handle if the control does not handle the gesture itself.
*/
/**
* @brief Retrieves the long press gesture detector of the control.
*
+ * @SINCE_1_0.0
* @return The long press gesture detector.
* @note Will return an empty handle if the control does not handle the gesture itself.
*/
/**
* @brief Sets the name of the style to be applied to the control.
*
+ * @SINCE_1_0.0
* @param[in] styleName A string matching a style described in a stylesheet.
*/
void SetStyleName( const std::string& styleName );
/**
* @brief Retrieves the name of the style to be applied to the control (if any).
- *
+ * @SINCE_1_0.0
* @return A string matching a style or an empty string.
*/
const std::string& GetStyleName() const;
/**
* @brief Sets the background color of the control.
*
- * @note if SetBackgroundImage is called later, this background color is removed.
- *
+ * @SINCE_1_0.0
* @param[in] color The required background color of the control
*
+ * @note if SetBackgroundImage is called later, this background color is removed.
+ *
* @note The background color fully blends with the actor color.
*/
void SetBackgroundColor( const Vector4& color );
/**
- * @brief Retrieves the background color of the control.
+ * @DEPRECATED_1_1.3
*
- * @deprecated DALi 1.1.3 API removed.
+ * @brief Retrieves the background color of the control.
*
+ * @SINCE_1_0.0
* @return The background color of the control.
*/
Vector4 GetBackgroundColor() const;
/**
* @brief Sets an image as the background of the control.
*
+ * @SINCE_1_0.0
* @param[in] image The image to set as the background.
*/
void SetBackgroundImage( Image image );
/**
* @brief Clears the background.
+ * @SINCE_1_0.0
*/
void ClearBackground();
* @endcode
* The return value of True, indicates that the event should be consumed.
* Otherwise the signal will be emitted on the next parent of the actor.
- * @pre The Control has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Control has been initialized.
*/
KeyEventSignalType& KeyEventSignal();
/**
- * @brief This signal is emitted when the control gets Key Input Focus
+ * @brief This signal is emitted when the control gets Key Input Focus.
*
* A callback of the following type may be connected:
* @code
* @endcode
* The return value of True, indicates that the event should be consumed.
* Otherwise the signal will be emitted on the next parent of the actor.
- * @pre The Control has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Control has been initialized.
*/
KeyInputFocusSignalType& KeyInputFocusGainedSignal();
* @endcode
* The return value of True, indicates that the event should be consumed.
* Otherwise the signal will be emitted on the next parent of the actor.
- * @pre The Control has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Control has been initialized.
*/
KeyInputFocusSignalType& KeyInputFocusLostSignal();
/**
* @brief Create an initialised Control.
*
+ * @SINCE_1_0.0
* @param[in] implementation The implementation for this control.
* @return A handle to a newly allocated Dali resource.
*
* @brief This constructor is used by CustomActor within Dali core to create additional Control handles
* using an Internal CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param [in] internal A pointer to a newly allocated Dali resource
*/
explicit Control(Dali::Internal::CustomActor* internal);
*
* @tparam T The handle class
* @tparam I The implementation class
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return Handle to a class T or an uninitialized handle.
* @see DownCast(BaseHandle)
* implementation of their class.
*
* @tparam I The implementation class
+ * @SINCE_1_0.0
* @param[in] internal Pointer to the Internal::CustomActor
*/
template<typename I>
*
* If the \e border parameter is set to \e true, the Dali::ImageActor's style is set to Dali::ImageActor::STYLE_NINE_PATCH.
*
+ * @SINCE_1_0.0
+ * @remarks This is an experimental feature and might not be supported in the next release. We do recommend not to use it.
* @param[in] color The ImageActor's color.
* @param[in] border If \e true, a border is created. By default, the value is set to \e false.
* @param[in] borderColor The color for the ImageActor's border. By default, the value is set to Color::WHITE.
* @param[in] borderSize The size for the ImageActor's border. By default, the value is set to 1 pixel. It supports under 10 pixel for clear result of gl blend
* @return a handle to the new ImageActor
+ * @see Control
*/
DALI_IMPORT_API ImageActor CreateSolidColorActor( const Vector4& color, bool border = false, const Vector4& borderColor = Color::WHITE, const unsigned int borderSize = 1 );
} // namespace Toolkit
*/
/**
- *
+ * @brief
* GaussianBlurView is a class for applying a render process that blurs an image.
*
* Basic idea:-
*
* Usage example:-
*
- * // initialise\n
- * GaussianBlurView gaussianBlurView = GaussianBlurView::New();\n
+ * @code
+ * // Initialise
+ * GaussianBlurView gaussianBlurView = GaussianBlurView::New();
*
- * // create and add some visible actors to the GaussianBlurView, all these child actors will therefore get blurred.\n
- * Image image = Image::New(...);\n
- * ImageActor imageActor = ImageActor::New(image);\n
- * gaussianBlurView.Add(imageActor);\n
- * ...\n
+ * // Create and add some visible actors to the GaussianBlurView, all these child actors will therefore get blurred.
+ * Image image = Image::New(...);
+ * ImageView imageView = ImageView::New(image);
+ * gaussianBlurView.Add(imageView);
+ * ...
*
- * // Start rendering the GaussianBlurView\n
- * Stage::GetCurrent().Add(gaussianBlurView);\n
- * gaussianBlurView.Activate();\n
- * ...\n
+ * // Start rendering the GaussianBlurView
+ * Stage::GetCurrent().Add(gaussianBlurView);
+ * gaussianBlurView.Activate();
+ * ...
*
- * // animate the strength of the blur - this can fade between no blur and full blur. See GetBlurStrengthPropertyIndex().\n
- * Animation blurAnimation = Animation::New( ... );\n
- * blurAnimation.AnimateTo( Property( gaussianBlurView, gaussianBlurView.GetBlurStrengthPropertyIndex() ), ... );\n
- * blurAnimation.Play();\n
+ * // Animate the strength of the blur - this can fade between no blur and full blur. See GetBlurStrengthPropertyIndex().
+ * Animation blurAnimation = Animation::New( ... );
+ * blurAnimation.AnimateTo( Property( gaussianBlurView, gaussianBlurView.GetBlurStrengthPropertyIndex() ), ... );
+ * blurAnimation.Play();
*
- * ...\n
- * // Stop rendering the GaussianBlurView\n
- * Stage::GetCurrent().Remove(gaussianBlurView);\n
- * gaussianBlurView.Deactivate();\n
+ * ...
+ * // Stop rendering the GaussianBlurView
+ * Stage::GetCurrent().Remove(gaussianBlurView);
+ * gaussianBlurView.Deactivate();
+ * @endcode
+ * @SINCE_1_0.0
+ * @remarks This is an experimental feature and might not be supported in the next release.
+ * We do recommend not to use this class.
*/
class DALI_IMPORT_API GaussianBlurView : public Control
{
public:
/**
- * Signal type for notifications
+ * @brief Signal type for notifications
+ * @SINCE_1_0.0
*/
typedef Signal< void (GaussianBlurView source) > GaussianBlurViewSignal;
/**
- * Create an uninitialized GaussianBlurView; this can be initialized with GaussianBlurView::New()
+ * @brief Create an uninitialized GaussianBlurView; this can be initialized with GaussianBlurView::New().
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
GaussianBlurView();
/**
- * Copy constructor. Creates another handle that points to the same real object
+ * @brief Copy constructor. Creates another handle that points to the same real object.
+ * @SINCE_1_0.0
*/
GaussianBlurView(const GaussianBlurView& handle);
/**
- * Assignment operator. Changes this handle to point to another real object
+ * @brief Assignment operator. Changes this handle to point to another real object.
+ * @SINCE_1_0.0
*/
GaussianBlurView& operator=(const GaussianBlurView& ZoomView);
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~GaussianBlurView();
/**
- * Downcast an Object handle to GaussianBlurView. If handle points to a GaussianBlurView the
+ * @brief Downcast a handle to GaussianBlurView handle.
+ *
+ * If handle points to a GaussianBlurView the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a GaussianBlurView or an uninitialized handle
+ * @return A handle to a GaussianBlurView or an uninitialized handle
*/
static GaussianBlurView DownCast( BaseHandle handle );
/**
- * Create an initialized GaussianBlurView, using default settings. The default settings are:-\n
+ * @brief Create an initialized GaussianBlurView, using default settings. The default settings are:-\n
*
* numSamples = 5\n
* blurBellCurveWidth = 1.5\n
* downsampleWidthScale = 0.5\n
* downsampleHeightScale = 0.5\n
* blurUserImage = false
+ * @SINCE_1_0.0
* @return A handle to a newly allocated Dali resource
*/
static GaussianBlurView New();
/**
- * Create an initialized GaussianBlurView.
+ * @brief Create an initialized GaussianBlurView.
+ * @SINCE_1_0.0
* @param numSamples The size of the Gaussian blur kernel (number of samples in horizontal / vertical blur directions).
* @param blurBellCurveWidth The constant controlling the Gaussian function, must be > 0.0. Controls the width of the bell curve, i.e. the look of the blur and also indirectly
* the amount of blurriness Smaller numbers for a tighter curve. Useful values in the range [0.5..3.0] - near the bottom of that range the curve is weighted heavily towards
bool blurUserImage = false);
/**
- * Adds a child Actor to this Actor.
- * NOTE! if the child already has a parent, it will be removed from old parent
- * and reparented to this actor. This may change childs position, color, shader effect,
- * scale etc as it now inherits them from this actor
+ * @brief Adds a child Actor to this Actor.
+ * @SINCE_1_0.0
+ * @param [in] child The child.
* @pre This Actor (the parent) has been initialized.
* @pre The child actor has been initialized.
* @pre The child actor is not the same as the parent actor.
* @pre The actor is not the Root actor
- * @param [in] child The child.
* @post The child will be referenced by its parent. This means that the child will be kept alive,
* even if the handle passed into this method is reset or destroyed.
+ * @note If the child already has a parent, it will be removed from old parent
+ * and reparented to this actor. This may change childs position, color, shader effect,
+ * scale etc as it now inherits them from this actor.
*/
void Add(Actor child);
/**
- * Removes a child Actor from this Actor.
+ * @brief Removes a child Actor from this Actor.
+ *
* If the actor was not a child of this actor, this is a no-op.
+ * @SINCE_1_0.0
+ * @param [in] child The child.
* @pre This Actor (the parent) has been initialized.
* @pre The child actor is not the same as the parent actor.
- * @param [in] child The child.
*/
void Remove(Actor child);
/**
- * Start rendering the GaussianBlurView. Must be called after you Add() it to the stage.
+ * @brief Start rendering the GaussianBlurView. Must be called after you Add() it to the stage.
+ * @SINCE_1_0.0
*/
void Activate();
/**
- * Render the GaussianBlurView once. Must be called after you Add() it to the stage.
+ * @brief Render the GaussianBlurView once.
+ *
+ * Must be called after you Add() it to the stage.
* Only works with a gaussian blur view created with blurUserImage = true.
* Listen to the Finished signal to determine when the rendering has completed.
+ * @SINCE_1_0.0
*/
void ActivateOnce();
/**
- * Stop rendering the GaussianBlurView. Must be called after you Remove() it from the stage.
+ * @brief Stop rendering the GaussianBlurView. Must be called after you Remove() it from the stage.
+ * @SINCE_1_0.0
*/
void Deactivate();
/**
- * Sets a custom image to be blurred and a render target to receive the blurred result. If this is called the children of the GaussianBlurObject will not be rendered blurred,
+ * @brief Sets a custom image to be blurred and a render target to receive the blurred result.
+ *
+ * If this is called the children of the GaussianBlurObject will not be rendered blurred,
* instead the inputImage will get blurred.
* To retrieve the blurred image the user can either pass a handle on a render target they own as the second parameter to SetUserImageAndOutputRenderTarget( ... ), or they
* can pass NULL for this parameter and instead call GetBlurredRenderTarget() which will return a handle on a render target created internally to the GaussianBlurView object.
- * @pre This object was created with a New( ... ) call where the blurUserImage argument was set to true. If this was not the case an exception will be thrown.
+ * @SINCE_1_0.0
* @param inputImage The image that the user wishes to blur.
* @param outputRenderTarget A render target to receive the blurred result. Passing NULL is allowed. See also GetBlurredRenderTarget().
+ * @pre This object was created with a New( ... ) call where the blurUserImage argument was set to true. If this was not the case an exception will be thrown.
*/
void SetUserImageAndOutputRenderTarget(Image inputImage, FrameBufferImage outputRenderTarget);
/**
- * Get the index of the property that can be used to fade the blur in / out. This is the overall strength of the blur.
+ * @brief Get the index of the property that can be used to fade the blur in / out.
+ *
+ * This is the overall strength of the blur.
* User can use this to animate the blur. A value of 0.0 is zero blur and 1.0 is full blur. Default is 1.0.
* Note that if you set the blur to 0.0, the result will be no blur BUT the internal rendering will still be happening. If you wish to turn the blur off, you should remove
* the GaussianBlurView object from the stage also.
+ * @SINCE_1_0.0
* @return Index of the property that can be used to fade the blur in / out
*/
Dali::Property::Index GetBlurStrengthPropertyIndex() const;
/**
- * Get the final blurred image.
+ * @brief Get the final blurred image.
+ *
* Use can call this function to get the blurred result as an image, to use as they wish. It is not necessary to call this unless you specifically require it.
- * @pre The user must call Activate() before the render target will be returned.
+ * @SINCE_1_0.0
* @return A handle on the blurred image, contained in a render target.
+ * @pre The user must call Activate() before the render target will be returned.
*/
FrameBufferImage GetBlurredRenderTarget() const;
/**
- * Set background color for the view. The background will be filled with this color.
+ * @brief Set background color for the view. The background will be filled with this color.
+ * @SINCE_1_0.0
* @param[in] color The background color.
*/
void SetBackgroundColor( const Vector4& color );
/**
- * Get the background color.
+ * @brief Get the background color.
+ * @SINCE_1_0.0
* @return The background color.
*/
Vector4 GetBackgroundColor() const;
public: // Signals
/**
- * If ActivateOnce has been called, then connect to this signal to be notified when the
+ * @brief If ActivateOnce has been called, then connect to this signal to be notified when the
* target actor has been rendered.
+ * @SINCE_1_0.0
* @return The Finished signal
*/
GaussianBlurViewSignal& FinishedSignal();
public:
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_0.0
* @param[in] implementation The UI Control implementation.
*/
DALI_INTERNAL GaussianBlurView( Internal::GaussianBlurView& implementation );
/**
- * Allows the creation of this UI Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this UI Control from an Internal::CustomActor pointer.
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL GaussianBlurView( Dali::Internal::CustomActor* internal );
*/
/**
- *
* @brief ImageView is a class for displaying an Image.
+ * @SINCE_1_0.0
+ *
*/
class DALI_IMPORT_API ImageView : public Control
{
public:
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices @SINCE_1_0.0
+
+ ANIMATABLE_PROPERTY_START_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX, ///< @SINCE_1_1.18
+ ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX + 1000 ///< Reserve animatable property indices, @SINCE_1_1.18
};
/**
* @brief An enumeration of properties belonging to the ImageView class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- RESOURCE_URL = PROPERTY_START_INDEX, ///< name "resourceUrl", @deprecated DALi 1.1.16 Use IMAGE instead. type string
- IMAGE, ///< name "image", @see SetImage(), type string if it is a url, map otherwise
+ // Event side properties
+
+ /**
+ * @DEPRECATED_1_1.16. Use IMAGE instead.
+ * @brief name "resourceUrl", type string
+ * @SINCE_1_0.0
+ */
+ RESOURCE_URL = PROPERTY_START_INDEX,
+ /**
+ * @brief name "image", type string if it is a url, map otherwise
+ * @SINCE_1_0.0
+ */
+ IMAGE,
+ /**
+ * @brief name "preMultipliedAlpha", type Boolean
+ * @SINCE_1_1.18
+ * @pre image must be initialized.
+ */
+ PRE_MULTIPLIED_ALPHA,
+
+ // Animatable properties
+
+
+ /**
+ * @brief name "pixelArea", type Vector4
+ * @details Pixel area is a relative value with the whole image area as [0.0, 0.0, 1.0, 1.0].
+ * @SINCE_1_0.18
+ */
+ PIXEL_AREA = ANIMATABLE_PROPERTY_START_INDEX,
};
};
/**
* @brief Create an uninitialized ImageView.
+ * @SINCE_1_0.0
*/
ImageView();
/**
* @brief Create an initialized ImageView.
*
+ * @SINCE_1_0.0
* @return A handle to a newly allocated Dali ImageView.
*
* @note ImageView will not display anything.
*
* If the handle is empty, ImageView will not display anything.
*
+ * @SINCE_1_0.0
* @param[in] image The Image to display.
* @return A handle to a newly allocated ImageView.
*/
*
* If the string is empty, ImageView will not display anything.
*
+ * @SINCE_1_0.0
* @param[in] url The url of the image resource to display.
* @return A handle to a newly allocated ImageView.
*/
*
* If the string is empty, ImageView will not display anything.
*
- * @since DALi 1.1.10
- *
+ * @SINCE_1_1.10
* @param[in] url The url of the image resource to display.
* @param [in] size The width and height to fit the loaded image to.
* @return A handle to a newly allocated ImageView.
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~ImageView();
/**
* @brief Copy constructor.
*
+ * @SINCE_1_0.0
* @param[in] imageView ImageView to copy. The copied ImageView will point at the same implementation
*/
ImageView( const ImageView& imageView );
/**
* @brief Assignment operator.
*
+ * @SINCE_1_0.0
* @param[in] imageView The ImageView to assign from.
* @return The updated ImageView.
*/
ImageView& operator=( const ImageView& imageView );
/**
- * @brief Downcast an Object handle to ImageView.
+ * @brief Downcast a handle to ImageView handle.
*
* If handle points to a ImageView the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a ImageView or an uninitialized handle
*/
* @brief Sets this ImageView from an Image
*
* If the handle is empty, ImageView will display nothing
+ * @SINCE_1_0.0
* @param[in] image The Image to display.
*/
void SetImage( Image image );
*
* If the URL is empty, ImageView will not display anything.
*
- * @since DALi 1.1.4
- *
+ * @SINCE_1_1.4
* @param[in] url The Image resource to display.
*/
void SetImage( const std::string& url );
*
* If the URL is empty, ImageView will not display anything.
*
- * @since DALi 1.1.10
- *
+ * @SINCE_1_1.10
* @param[in] url A URL to the image resource to display.
* @param [in] size The width and height to fit the loaded image to.
*/
void SetImage( const std::string& url, ImageDimensions size );
/**
- * @deprecated Gets the Image
+ * @DEPRECATED_1_1.4
+ * @brief Gets the Image
*
+ * @SINCE_1_0.0
+ * @remarks Calls to this method should be avoided as this may return an empty handle if the image has not been created yet.
* @return The Image currently set to this ImageView
*/
Image GetImage() const;
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The ImageView implementation.
*/
DALI_INTERNAL ImageView( Internal::ImageView& implementation );
/**
* @brief Allows the creation of this ImageView from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL ImageView( Dali::Internal::CustomActor* internal );
* All the geometry loaded with the control is automatically centered and scaled to fit
* the size of all the other controls. So the max is (0.5,0.5) and the min is (-0.5,-0.5)
*
- * @since DALi 1.1.4
+ * @SINCE_1_1.4
*/
class DALI_IMPORT_API Model3dView : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_1.4
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_1.4
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices @SINCE_1_1.4
- ANIMATABLE_PROPERTY_START_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX,
- ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX + 1000 ///< Reserve animatable property indices
+ ANIMATABLE_PROPERTY_START_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX, ///< @SINCE_1_1.4
+ ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX + 1000 ///< Reserve animatable property indices @SINCE_1_1.4
};
/**
* @brief An enumeration of properties belonging to the TextLabel class.
+ * @SINCE_1_1.4
*/
struct Property
{
enum
{
- GEOMETRY_URL = PROPERTY_START_INDEX, ///< name "geometryUrl", The path to the geometry file, type STRING
- MATERIAL_URL, ///< name "materialUrl", The path to the material file, type STRING
- IMAGES_URL, ///< name "imagesUrl", The path to the images directory, type STRING
- ILLUMINATION_TYPE, ///< name "illuminationType", The type of illumination, type INTEGER
- TEXTURE0_URL, ///< name "texture0Url", The path to first texture, type STRING
- TEXTURE1_URL, ///< name "texture1Url", The path to second texture, type STRING
- TEXTURE2_URL, ///< name "texture2Url", The path to third texture, type STRING
-
- LIGHT_POSITION = ANIMATABLE_PROPERTY_START_INDEX ///< name "lightPosition", The coordinates of the light, type Vector3
+ GEOMETRY_URL = PROPERTY_START_INDEX, ///< name "geometryUrl", The path to the geometry file, type STRING @SINCE_1_1.4
+ MATERIAL_URL, ///< name "materialUrl", The path to the material file, type STRING @SINCE_1_1.4
+ IMAGES_URL, ///< name "imagesUrl", The path to the images directory, type STRING @SINCE_1_1.4
+ ILLUMINATION_TYPE, ///< name "illuminationType", The type of illumination, type INTEGER @SINCE_1_1.4
+ TEXTURE0_URL, ///< name "texture0Url", The path to first texture, type STRING @SINCE_1_1.4
+ TEXTURE1_URL, ///< name "texture1Url", The path to second texture, type STRING @SINCE_1_1.4
+ TEXTURE2_URL, ///< name "texture2Url", The path to third texture, type STRING @SINCE_1_1.4
+
+ LIGHT_POSITION = ANIMATABLE_PROPERTY_START_INDEX ///< name "lightPosition", The coordinates of the light, type Vector3 @SINCE_1_1.4
};
};
/**
* @brief Create a new instance of a Model3dView control.
*
+ * @SINCE_1_1.4
* @return A handle to the new Model3dView control.
*/
static Model3dView New();
/**
* @brief Create a new instance of a Model3dView control.
*
+ * @SINCE_1_1.4
* @return A handle to the new Model3dView control.
*/
static Model3dView New( const std::string& objUrl, const std::string& mtlUrl, const std::string& imagesUrl );
*
* Only derived versions can be instantiated. Calling member
* functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_1.4
*/
Model3dView();
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_1.4
*/
~Model3dView();
/**
* @brief Copy constructor.
+ * @SINCE_1_1.4
*/
Model3dView( const Model3dView& model3dView );
/**
* @brief Assignment operator.
+ * @SINCE_1_1.4
*/
Model3dView& operator=( const Model3dView& model3dView );
* If handle points to a Model3dView the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_1.4
* @param[in] handle Handle to an object
* @return handle to a Model3dView or an uninitialized handle
*/
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_1.4
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL Model3dView( Internal::Model3dView& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_1.4
* @param[in] internal A pointer to the internal CustomActor.
*/
DALI_INTERNAL Model3dView( Dali::Internal::CustomActor* internal );
{
/**
- * PageFactory is an abstract interface for providing image actors to PageTurnView
+ * @brief PageFactory is an abstract interface for providing image actors to PageTurnView
* Each image actor is identified by a unique ID, and has a linear order from 0 to GetNumberOfPages()-1
*
- * @since DALi 1.1.4
+ * @SINCE_1_1.4
*/
class DALI_IMPORT_API PageFactory
{
public:
/**
- * Virtual destructor
+ * @brief Virtual destructor
+ * @SINCE_1_1.4
*/
virtual ~PageFactory(){};
/**
- * Query the number of pages available from the factory.
+ * @brief Query the number of pages available from the factory.
* The maximum available page has an ID of GetNumberOfPages()-1.
+ * @SINCE_1_1.4
*/
virtual unsigned int GetNumberOfPages() = 0;
/**
- * Create an actor to represent the page content.
+ * @brief Create an actor to represent the page content.
+ * @SINCE_1_1.4
* @param[in] pageId The ID of the page to create.
* @return An actor, or an uninitialized pointer if the ID is out of range.
*/
}
/**
- * PageTurnLandscapeView provides a page turn view in landscape mode
+ * @brief PageTurnLandscapeView provides a page turn view in landscape mode
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API PageTurnLandscapeView : public PageTurnView
{
public:
/**
- * Create an uninitialized PageTurnLandscapeView; this can be initialized with PageTurnLandscapeView::New()
+ * @brief Create an uninitialized PageTurnLandscapeView; this can be initialized with PageTurnLandscapeView::New()
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
PageTurnLandscapeView();
/**
- * Copy constructor.
+ * @brief Copy constructor.
+ * @SINCE_1_0.0
*/
PageTurnLandscapeView( const PageTurnLandscapeView& pageTurnLandscapeView );
/**
- * Assignment operator.
+ * @brief Assignment operator.
+ * @SINCE_1_0.0
*/
PageTurnLandscapeView& operator=( const PageTurnLandscapeView& pageTurnLandscapeView );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~PageTurnLandscapeView();
/**
- * Create an initialized PageTurnLandscapeView control
+ * @brief Create an initialized PageTurnLandscapeView control
+ * @SINCE_1_0.0
* @param[in] pageFactory The factory which provides PageTurnView with pages.
* @param[in] pageSize The size of the page
* @return A handle to the PageTurnLandscapeView control.
static PageTurnLandscapeView New( PageFactory& pageFactory, const Vector2& pageSize );
/**
- * Downcast an Object handle to PageTurnPortraitView. If handle points to a PageTurnLandscapeView the
+ * @brief Downcast an Object handle to PageTurnPortraitView. If handle points to a PageTurnLandscapeView the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a PageTurnLandscapeView or an uninitialized handle
*/
public: // Not intended for application developers
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL PageTurnLandscapeView( Internal::PageTurnLandscapeView& implementation );
/**
- * Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL PageTurnLandscapeView( Dali::Internal::CustomActor* internal );
}
/**
- * PageTurnLandscapeView provides a page turn view in portrait mode
+ * @brief PageTurnPortraitView provides a page turn view in portrait mode
*
- * @since DALi 1.1.4
+ * @SINCE_1_1.4
*/
class DALI_IMPORT_API PageTurnPortraitView : public PageTurnView
{
public:
/**
- * Create an uninitialized PageTurnPortraitView; this can be initialized with PageTurnPortraitView::New()
+ * @brief Create an uninitialized PageTurnPortraitView; this can be initialized with PageTurnPortraitView::New()
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_1.4
*/
PageTurnPortraitView();
/**
- * Copy constructor.
+ * @brief Copy constructor.
+ * @SINCE_1_1.4
*/
PageTurnPortraitView( const PageTurnPortraitView& pageTurnPortraitView );
/**
- * Assignment operator.
+ * @brief Assignment operator.
+ * @SINCE_1_1.4
*/
PageTurnPortraitView& operator=( const PageTurnPortraitView& pageTurnPortraitView );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_1.4
*/
~PageTurnPortraitView();
/**
- * Create an initialized PageTurnPortraitView control
+ * @brief Create an initialized PageTurnPortraitView control
+ * @SINCE_1_1.4
* @param[in] pageFactory The factory which provides PageTurnView with pages.
* @param[in] pageSize The size of the page
* @return A handle to the PageTurnPortraitView control.
static PageTurnPortraitView New( PageFactory& pageFactory, const Vector2& pageSize );
/**
- * Downcast an Object handle to PageTurnPortraitView. If handle points to a PageTurnPortraitView the
+ * @brief Downcast an Object handle to PageTurnPortraitView. If handle points to a PageTurnPortraitView the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_1.4
* @param[in] handle Handle to an object
* @return handle to a PageTurnPortraitView or an uninitialized handle
*/
public: // Not intended for application developers
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_1.4
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL PageTurnPortraitView( Internal::PageTurnPortraitView& implementation );
/**
- * Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @SINCE_1_1.4
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL PageTurnPortraitView( Dali::Internal::CustomActor* internal );
* | pagePanStarted | @ref PagePanStartedSignal() |
* | pagePanFinished | @ref PagePanFinishedSignal() |
*
- * @since DALi 1.1.4
+ * @SINCE_1_1.4
*/
class DALI_IMPORT_API PageTurnView : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_1.4
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_1.4
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices @SINCE_1_1.4
};
struct Property
{
enum
{
- PAGE_SIZE = PROPERTY_START_INDEX, ///< name "pageSize", type Vector2
- CURRENT_PAGE_ID, ///< name "currentPageId", type Integer
+ PAGE_SIZE = PROPERTY_START_INDEX, ///< name "pageSize", type Vector2 @SINCE_1_1.4
+ CURRENT_PAGE_ID, ///< name "currentPageId", type Integer @SINCE_1_1.4
/**
* The two values are the major&minor radius (in pixels) to form an ellipse shape.
* The top-left quarter of this ellipse is used to calculate spine normal for simulating shadow.
*/
- SPINE_SHADOW, ///< name "spineShadow", type Vector2
+ SPINE_SHADOW, ///< name "spineShadow", type Vector2 @SINCE_1_1.4
};
};
/**
- * Creates an empty PageTurnView handle. Only derived versions can be instantiated.
+ * @brief Creates an empty PageTurnView handle. Only derived versions can be instantiated.
* Calling member function with an uninitialized handle is not allowed.
+ * @SINCE_1_1.4
*/
PageTurnView();
/**
- * Copy constructor. Creates another handle that points to the same real object
+ * @brief Copy constructor. Creates another handle that points to the same real object
+ * @SINCE_1_1.4
* @param[in] handle Handle to copy from
*/
PageTurnView( const PageTurnView& handle );
/**
- * Assignment operator. Changes this handle to point to another real object
+ * @brief Assignment operator. Changes this handle to point to another real object
+ * @SINCE_1_1.4
*/
PageTurnView& operator=( const PageTurnView& handle );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_1.4
*/
~PageTurnView();
/**
- * Downcast an Object handle to PageTurnView.
+ * @brief Downcast an Object handle to PageTurnView.
* If handle points to an PageTurnView the downcast produces valid handle.
* If not the returned handle is left uninitialized.
+ * @SINCE_1_1.4
* @param[in] handle Handle to an object
* @return handle to a PageTurnView or an uninitialized handle
*/
typedef Signal< void ( PageTurnView ) > PagePanSignal;
/**
- * Signal emitted when a page has started to turn over.
+ * @brief Signal emitted when a page has started to turn over.
* A callback of the following type may be connected:
* @code
* void YourCallBackName( PageTurnView pageTurnView, unsigned int pageIndex, bool isTurningForward );
* @endcode
+ * @SINCE_1_1.4
* @return The signal to connect to
*/
PageTurnSignal& PageTurnStartedSignal();
/**
- * Signal emitted when a page has finished turning over.
+ * @brief Signal emitted when a page has finished turning over.
* A callback of the following type may be connected:
* @code
* void YourCallBackName( PageTurnView pageTurnView, unsigned int pageIndex, bool isTurningForward );
* @endcode
+ * @SINCE_1_1.4
* @return The signal to connect to
*/
PageTurnSignal& PageTurnFinishedSignal();
/**
- * Signal emitted when a page pan has commenced
+ * @brief Signal emitted when a page pan has commenced
* A callback of the following type may be connected:
* @code
* void YourCallBackName( PageTurnView pageTurnView );
* @endcode
+ * @SINCE_1_1.4
* @return The signal to connect to
*/
PagePanSignal& PagePanStartedSignal();
/**
- * Signal emitted when a page pan has finished
+ * @brief Signal emitted when a page pan has finished
* A callback of the following type may be connected:
* @code
* void YourCallBackName( PageTurnView pageTurnView );
* @endcode
+ * @SINCE_1_1.4
* @return The signal to connect to
*/
PagePanSignal& PagePanFinishedSignal();
public: // Not intended for application developers
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_1.4
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL PageTurnView(Internal::PageTurnView& implementation);
/**
- * Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @SINCE_1_1.4
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL PageTurnView(Dali::Internal::CustomActor* internal);
*/
/**
- * ScrollBar is a UI component that can be linked to the scrollable objects
+ * @brief ScrollBar is a UI component that can be linked to the scrollable objects
* indicating the current scroll position of the scrollable object.
*
* Signals
* |-------------------------------|--------------------------------------------|
* | panFinished | @ref PanFinishedSignal() |
* | scrollPositionIntervalReached | @ref ScrollPositionIntervalReachedSignal() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API ScrollBar : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the ScrollBar class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- SCROLL_DIRECTION = PROPERTY_START_INDEX, ///< name "scrollDirection", @see SetScrollDirection(), type std::string
- INDICATOR_HEIGHT_POLICY, ///< name "indicatorHeightPolicy", @see SetIndicatorHeightPolicy(), type std::string
- INDICATOR_FIXED_HEIGHT, ///< name "indicatorFixedHeight", @see SetIndicatorFixedHeight(), type float
- INDICATOR_SHOW_DURATION, ///< name "indicatorShowDuration", @see SetIndicatorShowDuration(), type float
- INDICATOR_HIDE_DURATION, ///< name "indicatorHideDuration", @see SetIndicatorHideDuration(), type float
- SCROLL_POSITION_INTERVALS ///< name "scrollPositionIntervals", @see SetScrollPositionIntervals() type Property::Array
+ SCROLL_DIRECTION = PROPERTY_START_INDEX, ///< name "scrollDirection", @see SetScrollDirection(), type std::string @SINCE_1_0.0
+ INDICATOR_HEIGHT_POLICY, ///< name "indicatorHeightPolicy", @see SetIndicatorHeightPolicy(), type std::string @SINCE_1_0.0
+ INDICATOR_FIXED_HEIGHT, ///< name "indicatorFixedHeight", @see SetIndicatorFixedHeight(), type float @SINCE_1_0.0
+ INDICATOR_SHOW_DURATION, ///< name "indicatorShowDuration", @see SetIndicatorShowDuration(), type float @SINCE_1_0.0
+ INDICATOR_HIDE_DURATION, ///< name "indicatorHideDuration", @see SetIndicatorHideDuration(), type float @SINCE_1_0.0
+ SCROLL_POSITION_INTERVALS ///< name "scrollPositionIntervals", @see SetScrollPositionIntervals() type Property::Array @SINCE_1_0.0
};
};
/**
* @brief Direction.
+ * @SINCE_1_0.0
*/
enum Direction
{
- Vertical = 0, ///< Scroll in the vertical direction
- Horizontal ///< Scroll in the horizontal direction
+ Vertical = 0, ///< Scroll in the vertical direction @SINCE_1_0.0
+ Horizontal ///< Scroll in the horizontal direction @SINCE_1_0.0
};
/**
* @brief Indicator height policy.
+ * @SINCE_1_0.0
*/
enum IndicatorHeightPolicy
{
- Variable = 0, ///< Variable height changed dynamically according to the length of scroll content
- Fixed ///< Fixed height regardless of the length of scroll content
+ Variable = 0, ///< Variable height changed dynamically according to the length of scroll content @SINCE_1_0.0
+ Fixed ///< Fixed height regardless of the length of scroll content @SINCE_1_0.0
};
/**
* @brief Create an uninitialized ScrollBar; this can be initialized with ScrollBar::New()
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
ScrollBar();
/**
* @brief Copy constructor.
+ * @SINCE_1_0.0
*/
ScrollBar( const ScrollBar& scrollBar );
/**
* @brief Assignment operator.
+ * @SINCE_1_0.0
*/
ScrollBar& operator=( const ScrollBar& scrollBar );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~ScrollBar();
/**
* @brief Create an initialized ScrollBar
+ * @SINCE_1_0.0
* @param[in] direction The direction of scroll bar (either vertically or horizontally).
* @return A pointer to the created ScrollBar.
*/
static ScrollBar New(Direction direction = Vertical);
/**
- * @brief Downcast an Object handle to ScrollBar. If handle points to a ScrollBar the
+ * @brief Downcast a handle to ScrollBar handle.
+ *
+ * If handle points to a ScrollBar the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a ScrollBar or an uninitialized handle
*/
*
* * @pre The handle to the object owing the scroll properties has been initialised and the property index must be vaild.
*
+ * @SINCE_1_0.0
* @param[in] handle The handle of the object owing the scroll properties.
* @param[in] propertyScrollPosition The index of the scroll position property (The scroll position, type float).
* @param[in] propertyMinScrollPosition The index of the minimum scroll position property (The minimum scroll position, type float).
/**
* @brief Sets the indicator of scroll bar.
*
+ * @SINCE_1_0.0
+ * @param[in] indicator The indicator that moves to indicate the current scroll position.
* @pre The scroll bar actor has been initialised.
*
- * @param[in] indicator The indicator that moves to indicate the current scroll position.
*/
void SetScrollIndicator( Actor indicator );
/**
* @brief Gets the indicator of scroll bar.
*
+ * @SINCE_1_0.0
+ * @return The indicator indicates the current scroll position of the scrollable content.
* @pre The scroll bar actor has been initialised.
*
- * @return The indicator indicates the current scroll position of the scrollable content.
*/
Actor GetScrollIndicator();
* @brief Sets the list of values to get notification when the current scroll position of the scrollable
* object goes above or below any of these values.
*
+ * @SINCE_1_0.0
+ * @param[in] positions List of values to receive notifications for when the current scroll position crosses them
* @pre The scroll bar actor has been initialised.
*
- * @param[in] positions List of values to receive notifications for when the current scroll position crosses them
*/
void SetScrollPositionIntervals( const Dali::Vector<float>& positions );
* @brief Gets the list of values to receive notifications when the current scroll position of the scrollable
* object goes above or below any of these values.
*
+ * @SINCE_1_0.0
+ * @return The list of values to receive notifications for when the current scroll position crosses them
* @pre The scroll bar actor has been initialised.
*
- * @return The list of values to receive notifications for when the current scroll position crosses them
*/
Dali::Vector<float> GetScrollPositionIntervals() const;
/**
* @brief Sets the direction of scroll bar to scroll either vertically or horizontally.
*
+ * @SINCE_1_0.0
+ * @param[in] direction The direction of scroll bar (either vertically or horizontally).
* @pre The scroll bar actor has been initialised.
*
- * @param[in] direction The direction of scroll bar (either vertically or horizontally).
*/
void SetScrollDirection( Direction direction );
/**
* @brief Gets the direction of scroll bar.
*
+ * @SINCE_1_0.0
* @return The direction of scroll bar.
*/
Direction GetScrollDirection() const;
/**
* @brief Sets the height policy of scroll indicator to have either variable or fixed height.
*
+ * @SINCE_1_0.0
+ * @param[in] policy The height policy of scroll indicator
* @pre The scroll bar actor has been initialised.
*
- * @param[in] policy The height policy of scroll indicator
*/
void SetIndicatorHeightPolicy( IndicatorHeightPolicy policy );
/**
* @brief Gets the height policy of scroll indicator.
*
+ * @SINCE_1_0.0
* @return The height policy of scroll indicator
*/
IndicatorHeightPolicy GetIndicatorHeightPolicy() const;
/**
* @brief Sets the fixed height of scroll indicator.
+ *
* Normally the height of scroll indicator is changed dynamically according to the length of scroll content.
* However, when the height policy of scroll indicator is set to be fixed, the height will keep fixed
* regardless of the length of scroll content.
*
+ * @SINCE_1_0.0
+ * @param[in] height The fixed height of the scroll indicator
* @pre The scroll bar actor has been initialised.
*
- * @param[in] height The fixed height of the scroll indicator
*/
void SetIndicatorFixedHeight( float height );
/**
* @brief Gets the fix height of scroll indicator.
+ * @SINCE_1_0.0
* @return The fixed height of the scroll indicator
*/
float GetIndicatorFixedHeight() const;
/**
* @brief Sets the duration in second for the scroll indicator to become fully visible
*
+ * @SINCE_1_0.0
+ * @param[in] durationSeconds The duration for the scroll indicator to become fully visible
* @pre The scroll bar actor has been initialised; durationSeconds must be zero or greater; zero means the indicator will be shown instantly.
*
- * @param[in] durationSeconds The duration for the scroll indicator to become fully visible
*/
void SetIndicatorShowDuration( float durationSeconds );
/**
* @brief Gets the duration in second for the scroll indicator to become fully visible
+ * @SINCE_1_0.0
* @return The duration for the scroll indicator to become fully visible
*/
float GetIndicatorShowDuration() const;
/**
* @brief Sets the duration in second for the scroll indicator to become fully invisible
*
+ * @SINCE_1_0.0
+ * @param[in] durationSeconds The duration for the scroll indicator to become fully invisible
* @pre The scroll bar actor has been initialised; durationSeconds must be zero or greater; zero means the indicator will be hidden instantly.
*
- * @param[in] durationSeconds The duration for the scroll indicator to become fully invisible
*/
void SetIndicatorHideDuration( float durationSeconds );
/**
* @brief Gets the duration in second for the scroll indicator to become fully invisible
+ * @SINCE_1_0.0
* @return The duration for the scroll indicator to become fully invisible
*/
float GetIndicatorHideDuration() const;
/**
* @brief Shows the scroll indicator
+ * @SINCE_1_0.0
*/
void ShowIndicator();
/**
* @brief Hides the scroll indicator
+ * @SINCE_1_0.0
*/
void HideIndicator();
/**
* @brief Signal emitted when panning is finished on the scroll indicator.
+ *
* Signal only emitted when the source of the scroll position properties are set.
*
* A callback of the following type may be connected:
* @code
* void YourCallbackName();
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
ScrollBar::PanFinishedSignalType& PanFinishedSignal();
/**
* @brief Signal emitted when the current scroll position of the scrollable content
* goes above or below the values specified by SCROLL_POSITION_INTERVALS property.
+ *
* Signal only emitted when the source of the scroll position properties are set.
*
* A callback of the following type may be connected:
* @code
* void YourCallbackName(float currentScrollPosition);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
ScrollBar::ScrollPositionIntervalReachedSignalType& ScrollPositionIntervalReachedSignal();
public: // Not intended for application developers
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL ScrollBar( Internal::ScrollBar& implementation );
/**
- * Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL ScrollBar( Dali::Internal::CustomActor* internal );
* @{
*/
+/**
+ * @brief Default item layout mode.
+ * @SINCE_1_0.0
+ */
namespace DefaultItemLayout
{
enum Type
{
- DEPTH, ///< Items arranged in a grid, scrolling along the Z-Axis.
- GRID, ///< Items arranged in a grid, scrolling along the Y-Axis.
- LIST, ///< One item per line, scrolling along the Y-Axis.
- SPIRAL ///< Items arranged in a spiral, centered around the Y-Axis.
+ DEPTH, ///< Items arranged in a grid, scrolling along the Z-Axis. @SINCE_1_0.0
+ GRID, ///< Items arranged in a grid, scrolling along the Y-Axis. @SINCE_1_0.0
+ LIST, ///< One item per line, scrolling along the Y-Axis. @SINCE_1_0.0
+ SPIRAL ///< Items arranged in a spiral, centered around the Y-Axis. @SINCE_1_0.0
};
/**
- * @brief Creates a built-in default item-layout
+ * @brief Creates a built-in default item-layout.
*
+ * @SINCE_1_0.0
* @param[in] type The type of layout required.
*
* @return An ItemLayoutPtr to the newly created layout.
/**
* @brief ItemFactory is for providing actors to ItemView.
+ *
* Each actor is identified by a unique ID, and has a linear order from 0 to GetNumberOfItems()-1.
+ * @SINCE_1_0.0
*/
class ItemFactory
{
/**
* @brief Virtual destructor.
+ * @SINCE_1_0.0
*/
DALI_EXPORT_API virtual ~ItemFactory() {};
* @brief Query the number of items available from the factory.
*
* The maximum available item has an ID of GetNumberOfItems() - 1.
+ * @SINCE_1_0.0
* @return the number of items
*/
virtual unsigned int GetNumberOfItems() = 0;
/**
* @brief Create an Actor to represent a visible item.
*
+ * @SINCE_1_0.0
* @param[in] itemId The ID of the newly visible item.
* @return An actor, or an uninitialized pointer if the ID is out of range.
*/
/**
* @brief Notify the factory the actor representing the item is removed from ItemView.
*
+ * @SINCE_1_0.0
* @param[in] itemId The ID of the released item.
* @param[in] actor The actor that represents the released item.
*/
virtual void ItemReleased(unsigned int itemId, Actor actor) {};
/**
- * Retrieve the extension for this control
+ * @brief Retrieve the extension for this control.
*
+ * @SINCE_1_0.0
* @return The extension if available, NULL otherwise
*/
virtual Extension* GetExtension()
class ItemLayout;
-typedef IntrusivePtr<ItemLayout> ItemLayoutPtr; ///< Pointer to a Dali::Toolkit::ItemLayout object
+typedef IntrusivePtr<ItemLayout> ItemLayoutPtr; ///< Pointer to a Dali::Toolkit::ItemLayout object @SINCE_1_0.0
/**
* @brief A support class for managing ranges of items.
+ * @SINCE_1_0.0
*/
struct ItemRange
{
/**
* @brief Create a range of item identifiers.
*
+ * @SINCE_1_0.0
* @param[in] beginItem The first item within the range.
* @param[in] endItem The past-the-end item.
*/
/**
* @brief Copy Constructor.
*
+ * @SINCE_1_0.0
* @param[in] copy ItemRange we should copy from.
*/
ItemRange(const ItemRange& copy)
/**
* @brief Assignment operator.
*
+ * @SINCE_1_0.0
* @param[in] range The Range to assign from.
* @return The updated range.
*/
/**
* @brief Test whether an item is within the range.
*
+ * @SINCE_1_0.0
* @param[in] itemId The item identifier.
* @return True if the item is within the range.
*/
/**
* @brief Create the intersection of two ranges.
*
+ * @SINCE_1_0.0
* @param[in] second The second range.
* @return The intersection.
*/
*
* An ItemLayout also describes the direction of input gestures, used to scroll through the layout.
* Whilst scrolling, the layout provides a range of items that are within a layout-area (3D bounding volume).
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API ItemLayout : public RefObject
{
/**
* @brief Virtual destructor.
+ * @SINCE_1_0.0
*/
DALI_IMPORT_API virtual ~ItemLayout();
/**
* @brief Set the orientation of the layout.
*
+ * @SINCE_1_0.0
* @param[in] orientation The orientation of the layout.
*/
DALI_IMPORT_API void SetOrientation(ControlOrientation::Type orientation);
/**
* @brief Query the orientation of the layout.
*
+ * @SINCE_1_0.0
* @return the orientation of the layout.
*/
DALI_IMPORT_API ControlOrientation::Type GetOrientation() const;
*
* This will return the default size for the layout unless overridden by calling SetItemSize().
*
- * @note layout-position is not provided as a parameter, since applying size constraints is not recommended.
- * Animating to target-sizes is preferable, since this allows controls to perform layouting without constraints.
+ * @SINCE_1_0.0
* @param[in] itemId The ID of an item in the layout.
* @param[in] layoutSize The layout size
* @param[out] itemSize The target size of an item.
+ * @note layout-position is not provided as a parameter, since applying size constraints is not recommended.
+ * Animating to target-sizes is preferable, since this allows controls to perform layouting without constraints.
*/
DALI_IMPORT_API void GetItemSize( unsigned int itemId, const Vector3& layoutSize, Vector3& itemSize ) const;
/**
* @brief Overrides the default size for the layout.
*
+ * @SINCE_1_0.0
* @param[in] itemSize The size of each item.
*/
DALI_IMPORT_API void SetItemSize( const Vector3& itemSize );
* @brief Query the minimum valid layout position; this is a negative value.
*
* When scrolling, the first item will move within the range 0 to GetMinimumLayoutPosition().
+ * @SINCE_1_0.0
* @param[in] numberOfItems The current number of items in the layout.
* @param[in] layoutSize The size of the layout area.
* @return The minimum layout position.
*
* This anchor position is the position where all the items in the layout are aligned to
* their rounded layout positions in integer.
+ * @SINCE_1_0.0
* @param[in] layoutPosition The layout position.
* @return The closest anchor position for the given layout position.
*/
* @brief Query the layout position for the first item in the layout to move to when the layout
* needs to scroll to a particular item.
*
+ * @SINCE_1_0.0
* @param[in] itemId The ID of an item in the layout.
* @return The layout position for the first item in the layout to move to.
*/
/**
* @brief Query the items within a given layout-area.
*
+ * @SINCE_1_0.0
* @param[in] firstItemPosition The layout-position of the first item in the layout.
* @param[in] layoutSize The size of the layout area.
* @return The ID of the first & last visible item.
* implementations should provide their own version of this function
* to ensure proper functionality of internal toolkit systems.
*
+ * @SINCE_1_0.0
* @param[in] itemID id of the item to bring within the viewable screen area
* @param[in] currentLayoutPosition the current layout position of the item view instance
* @param[in] layoutSize the current size of the item view instance
/**
* @brief Query the number of items that should be reserved, for scrolling purposes.
*
+ * @SINCE_1_0.0
* @param[in] layoutSize The size of the layout area.
* @return The number of extra items. ItemView will populate itself with actors within the layout-area
* (see GetItemsWithinArea), plus this number of additional items on either-side.
/**
* @brief Retrieve the default size of an item in the layout.
*
- * @note layout-position is not provided as a parameter, since applying size constraints is not recommended.
- * Animating to target-sizes is preferable, since this allows controls to perform layouting without constraints.
+ * @SINCE_1_0.0
* @param[in] itemId The ID of an item in the layout.
* @param[in] layoutSize The layout size
* @param[out] itemSize The target size of an item.
+ * @note layout-position is not provided as a parameter, since applying size constraints is not recommended.
+ * Animating to target-sizes is preferable, since this allows controls to perform layouting without constraints.
*/
virtual void GetDefaultItemSize( unsigned int itemId, const Vector3& layoutSize, Vector3& itemSize ) const = 0;
*
* When an input gesture follows this direction, the layout-position of items will be increased.
* If the input gesture points in the opposite direction, then the layout-positions will decrease.
+ * @SINCE_1_0.0
* @return The scroll direction in degrees.
*/
virtual Degree GetScrollDirection() const = 0;
* position of actors will be moved by 1.
* Therefore, the bigger the factor is, the faster the scroll speed will be.
*
+ * @SINCE_1_0.0
* @return The scroll speed factor of the layout.
*/
virtual float GetScrollSpeedFactor() const = 0;
* @brief Query the maximum swipe speed in pixels per second.
*
* Swipe gestures will be clamped when exceeding this speed limit.
+ * @SINCE_1_0.0
* @return speed The maximum swipe speed.
*/
virtual float GetMaximumSwipeSpeed() const = 0;
* This is the time taken to animate each
* item to its next layout position (e.g. from 1.0 to 2.0) when a flick animation is triggered
* by a swipe gesture.
+ * @SINCE_1_0.0
* @return The duration of the flick animation.
*/
virtual float GetItemFlickAnimationDuration() const = 0;
/**
* @brief Gets the id of the next item for KeyboardFocusManager to focus on depending on the inputted item ID.
*
+ * @SINCE_1_0.0
* @param[in] itemID The current focused item
* @param[in] maxItems The maximum number of items in the list
* @param[in] direction The directional key pressed on the keyboard
* position of actors will be moved by 1.
* Therefore, the bigger the factor is, the faster the flick speed will be.
*
+ * @SINCE_1_0.0
* @return The scroll speed factor of the layout.
*/
DALI_IMPORT_API virtual float GetFlickSpeedFactor() const;
*
* @param[in] actor The actor to constrain.
* @param[in] itemId The ID of the item represented by the actor.
- * @param[in] layoutSize the current size of the item view instance.
+ * @param[in] layoutSize The current size of the item view instance.
* @param[in] itemViewActor The item view instance which requests the application of constraints.
*/
DALI_IMPORT_API virtual void ApplyConstraints( Actor& actor, const int itemId, const Vector3& layoutSize, const Actor& itemViewActor ) = 0;
/**
* @brief Gets the position of a given item
*
- * @param[in] itemID id of the item we want to get its position
- * @param[in] currentLayoutPosition the current layout position of the item view instance
- * @param[in] layoutSize the current size of the item view instance
+ * @SINCE_1_0.0
+ * @param[in] itemID The id of the item we want to get its position
+ * @param[in] currentLayoutPosition The current layout position of the item view instance
+ * @param[in] layoutSize The current size of the item view instance
* @return The item position (x,y,z)
*/
DALI_IMPORT_API virtual Vector3 GetItemPosition(int itemID, float currentLayoutPosition, const Vector3& layoutSize) const = 0;
/**
- * Retrieve the extension for this layout.
+ * @brief Retrieve the extension for this layout.
*
+ * @SINCE_1_0.0
* @return The extension if available, NULL otherwise
*/
virtual Extension* GetExtension()
/**
* @brief Create a new ItemLayout; Only derived versions are instantiatable.
+ * @SINCE_1_0.0
*/
DALI_IMPORT_API ItemLayout();
private:
/**
- * Don't allow copy constructor
+ * @brief Don't allow copy constructor
+ * @SINCE_1_0.0
*/
ItemLayout( const ItemLayout& handle );
/**
- * Don't allow copy operator
+ * @brief Don't allow copy operator
+ * @SINCE_1_0.0
*/
ItemLayout& operator=( const ItemLayout& handle );
* @{
*/
-typedef unsigned int ItemId; ///< Unique identity for each item in the view.
+typedef unsigned int ItemId; ///< Unique identity for each item in the view. @SINCE_1_0.0
-typedef std::vector<ItemId> ItemIdContainer;
-typedef ItemIdContainer::iterator ItemIdIter;
-typedef ItemIdContainer::const_iterator ConstItemIdIter;
+typedef std::vector<ItemId> ItemIdContainer; ///< Item id container type @SINCE_1_0.0
+typedef ItemIdContainer::iterator ItemIdIter; ///< Item id iterator type @SINCE_1_0.0
+typedef ItemIdContainer::const_iterator ConstItemIdIter; ///< Item id const iterator type @SINCE_1_0.0
-typedef std::pair<ItemId, Actor> Item;
+typedef std::pair<ItemId, Actor> Item; ///< Item type @SINCE_1_0.0
-typedef std::vector<Item> ItemContainer;
-typedef ItemContainer::iterator ItemIter;
-typedef ItemContainer::const_iterator ConstItemIter;
+typedef std::vector<Item> ItemContainer; ///< Item container type @SINCE_1_0.0
+typedef ItemContainer::iterator ItemIter; ///< Item iterator type @SINCE_1_0.0
+typedef ItemContainer::const_iterator ConstItemIter; ///< Item const iterator type @SINCE_1_0.0
class ItemView;
class ItemLayout;
* | %Signal Name | Method |
* |---------------------------------|--------------------------------------------|
* | layoutActivated | @ref LayoutActivatedSignal() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API ItemView : public Scrollable
enum PropertyRange
{
+ PROPERTY_START_INDEX = Toolkit::Scrollable::PROPERTY_END_INDEX + 1, ///< @SINCE_1_1.18
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices, @SINCE_1_1.18
+
ANIMATABLE_PROPERTY_START_INDEX = Toolkit::Scrollable::ANIMATABLE_PROPERTY_END_INDEX + 1,
- ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_START_INDEX + 1000 ///< Reserve animatable property indices
+ ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_START_INDEX + 1000 ///< Reserve animatable property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the ScrollView class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- LAYOUT_POSITION = ANIMATABLE_PROPERTY_START_INDEX, ///< Property, name "layoutPosition", type float
- SCROLL_SPEED, ///< Property, name "scrollSpeed", type float
- OVERSHOOT, ///< Property, name "overshoot", type float
- SCROLL_DIRECTION, ///< Property, name "scrollDirection", type Vector2
- LAYOUT_ORIENTATION, ///< Property, name "layoutOrientation", type integer
- SCROLL_CONTENT_SIZE ///< Property, name "scrollContentSize", type float
+ // Event side properties
+ MINIMUM_SWIPE_SPEED = PROPERTY_START_INDEX, ///< Property, name "minimumSwipeSpeed", @see SetMinimumSwipeSpeed(), type float, @SINCE_1_1.18
+ MINIMUM_SWIPE_DISTANCE, ///< Property, name "minimumSwipeDistance", @see SetMinimumSwipeDistance(), type float, @SINCE_1_1.18
+ WHEEL_SCROLL_DISTANCE_STEP, ///< Property, name "wheelScrollDistanceStep", @see SetWheelScrollDistanceStep(), type float, @SINCE_1_1.18
+ SNAP_TO_ITEM_ENABLED, ///< Property, name "snapToItemEnabled", @see SetAnchoring(), type bool, @SINCE_1_1.18
+ REFRESH_INTERVAL, ///< Property, name "refreshInterval", @see SetRefreshInterval(), type float, @SINCE_1_1.18
+
+ // Animatable properties
+ LAYOUT_POSITION = ANIMATABLE_PROPERTY_START_INDEX, ///< Property, name "layoutPosition", type float @SINCE_1_0.0
+ SCROLL_SPEED, ///< Property, name "scrollSpeed", type float @SINCE_1_0.0
+ OVERSHOOT, ///< Property, name "overshoot", type float @SINCE_1_0.0
+ SCROLL_DIRECTION, ///< Property, name "scrollDirection", type Vector2 @SINCE_1_0.0
+ LAYOUT_ORIENTATION, ///< Property, name "layoutOrientation", type integer @SINCE_1_0.0
+ SCROLL_CONTENT_SIZE ///< Property, name "scrollContentSize", type float @SINCE_1_0.0
};
};
* @brief Create an uninitialized ItemView; this can be initialized with ItemView::New().
*
* Calling member functions with an uninitialized Dali::Object is not allowed.
+ * @SINCE_1_0.0
*/
ItemView();
/**
* @brief Copy constructor.
+ * @SINCE_1_0.0
*/
ItemView( const ItemView& itemView );
/**
* @brief Assignment operator.
+ * @SINCE_1_0.0
*/
ItemView& operator=( const ItemView& itemView );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~ItemView();
/**
* @brief Create an initialized ItemView.
*
+ * @SINCE_1_0.0
* @param[in] factory The factory which provides ItemView with items.
* @return A handle to a newly allocated Dali resource.
*/
static ItemView New(ItemFactory& factory);
/**
- * @brief Downcast an Object handle to ItemView.
+ * @brief Downcast a handle to ItemView handle.
*
* If handle points to a ItemView the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a ItemView or an uninitialized handle
+ * @return A handle to a ItemView or an uninitialized handle
*/
static ItemView DownCast( BaseHandle handle );
/**
* @brief Query the number of layouts.
*
+ * @SINCE_1_0.0
* @return The number of layouts.
*/
unsigned int GetLayoutCount() const;
/**
* @brief Add a layout.
*
+ * @SINCE_1_0.0
* @param[in] layout The layout.
*/
void AddLayout(ItemLayout& layout);
/**
* @brief Remove a layout.
*
- * @pre layoutIndex is less than GetLayoutCount().
+ * @SINCE_1_0.0
* @param[in] layoutIndex The index of one of the ItemView layouts.
+ * @pre layoutIndex is less than GetLayoutCount().
*/
void RemoveLayout(unsigned int layoutIndex);
/**
* @brief Retrieve a layout.
*
- * @pre layoutIndex is less than GetLayoutCount().
+ * @SINCE_1_0.0
* @param[in] layoutIndex The index of the layout to retrieve.
* @return The layout
+ * @pre layoutIndex is less than GetLayoutCount().
*/
ItemLayoutPtr GetLayout(unsigned int layoutIndex) const;
/**
* @brief Retrieve the currently active layout, if any.
*
+ * @SINCE_1_0.0
* @return The layout, or an uninitialized pointer if no layout is active.
*/
ItemLayoutPtr GetActiveLayout() const;
/**
* @brief Retrieve the current layout-position of an item in the ItemView.
*
+ * @SINCE_1_0.0
* @param[in] itemId The item identifier.
* @return The current layout-position.
*/
* This is done by applying constraints from the new layout, and
* removing constraints from the previous layout.
*
- * @pre layoutIndex is less than GetLayoutCount().
- * @pre durationSeconds is greater or equal to zero.
+ * @SINCE_1_0.0
* @param[in] layoutIndex The index of one of the ItemView layouts.
* @param[in] targetSize The target ItemView & layout size.
* @param[in] durationSeconds The time taken to relayout in seconds (zero for immediate).
+ * @pre layoutIndex is less than GetLayoutCount().
+ * @pre durationSeconds is greater or equal to zero.
*/
void ActivateLayout(unsigned int layoutIndex, Vector3 targetSize, float durationSeconds);
* @brief Deactivate the current layout, if any.
*
* The constraints applied by the layout will be removed.
+ * @SINCE_1_0.0
*/
void DeactivateCurrentLayout();
* @brief Set the minimum swipe speed in pixels per second; A pan
* gesture must exceed this to trigger a swipe.
*
+ * @SINCE_1_0.0
* @param[in] speed The minimum swipe speed
*/
void SetMinimumSwipeSpeed(float speed);
/**
* @brief Get the minimum swipe speed in pixels per second.
*
+ * @SINCE_1_0.0
* @return The minimum swipe speed
*/
float GetMinimumSwipeSpeed() const;
* @brief Set the minimum swipe distance in actor coordinates; A pan
* gesture must exceed this to trigger a swipe.
*
+ * @SINCE_1_0.0
* @param[in] distance The minimum swipe distance.
*/
void SetMinimumSwipeDistance(float distance);
/**
* @brief Get the minimum swipe distance in actor coordinates.
*
+ * @SINCE_1_0.0
* @return The minimum swipe distance
*/
float GetMinimumSwipeDistance() const;
/**
* @brief Set the step of scroll distance in actor coordinates for each wheel event received.
*
+ * @SINCE_1_0.0
* @param[in] step The step of scroll distance(pixel).
*/
void SetWheelScrollDistanceStep(float step);
/**
* @brief Get the step of scroll distance in actor coordinates for each wheel event received.
*
+ * @SINCE_1_0.0
* @return The step of scroll distance(pixel)
*/
float GetWheelScrollDistanceStep() const;
* The anchor position is the position where all the items in the layout
* are aligned to their closest rounded layout positions in integer.
*
+ * @SINCE_1_0.0
* @param[in] enabled Whether the anchor animation is enabled or not.
*/
void SetAnchoring(bool enabled);
/**
* @brief Get whether the anchor animation is enabled or not.
*
+ * @SINCE_1_0.0
* @return Whether the anchor animation is enabled or not.
*/
bool GetAnchoring() const;
* This is the time taken to reach the nearest anchor position after
* a drag or swipe gesture ends.
*
- * @pre durationSeconds must be greater than zero.
+ * @SINCE_1_0.0
* @param[in] durationSeconds The duration of the anchor animation in seconds.
+ * @pre durationSeconds must be greater than zero.
*/
void SetAnchoringDuration(float durationSeconds);
/**
* @brief Get the duration of the anchor animation in seconds.
*
+ * @SINCE_1_0.0
* @return The duration of the anchor animation
*/
float GetAnchoringDuration() const;
/**
* @brief Scroll the current layout to a particular item.
*
+ * @SINCE_1_0.0
+ * @param[in] itemId The ID of an item in the layout.
+ * @param[in] durationSeconds How long the scrolling takes in seconds.
* @pre durationSeconds must be zero or greater; zero means the layout should scroll to the particular item instantly.
* If calling this with zero second of duration immediately after calling ActivateLayout, it might not work unless
* the duration of relayout animation for ActivateLayout is also set to be zero.
- * @param[in] itemId The ID of an item in the layout.
- * @param[in] durationSeconds How long the scrolling takes in seconds.
*/
void ScrollToItem(ItemId itemId, float durationSeconds);
/**
- * @brief Set the interval between refreshes. When the layout-position of items is changed by this interval,
+ * @brief Set the interval between refreshes.
+ *
+ * When the layout-position of items is changed by this interval,
* new items are requested from ItemFactory.
*
+ * @SINCE_1_0.0
* @param[in] intervalLayoutPositions The refresh interval in layout position.
*/
void SetRefreshInterval(float intervalLayoutPositions);
/**
* @brief Get the interval between refreshes in layout position.
*
+ * @SINCE_1_0.0
* @return The refresh interval
*/
float GetRefreshInterval() const;
/**
* @brief Do a refresh of the item view.
+ * @SINCE_1_0.0
*/
void Refresh();
/**
* @brief Given the Item ID, this returns the accompanying actor.
*
+ * @SINCE_1_0.0
* @param[in] itemId The Item ID of the actor required.
* @return The Actor corresponding to the Item ID.
*/
/**
* @brief Returns the Item ID of the specified actor.
*
+ * @SINCE_1_0.0
* @param[in] actor The actor whose Item ID is required.
* @return The Item ID of the item.
* @pre The actor should be an item of ItemView.
* ID 2 - ActorB ID 2 - ActorZ !
* ID 3 - ActorC ID 3 - ActorB
* ID 4 - ActorC
- * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
+ * @SINCE_1_0.0
* @param[in] newItem The item to insert.
* @param[in] durationSeconds How long the relayout takes in seconds.
+ * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
*/
void InsertItem(Item newItem, float durationSeconds);
/**
* @brief Insert a set of items; this is more efficient than calling InsertItem() repeatedly.
*
- * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
+ * @SINCE_1_0.0
* @param[in] newItems The items to insert.
* @param[in] durationSeconds How long the relayout takes in seconds.
+ * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
*/
void InsertItems(const ItemContainer& newItems, float durationSeconds);
* ID 2 - ActorB ID 2 - ActorC (previously ID 3)
* ID 3 - ActorC ID 3 - ActorB (previously ID 4)
* ID 4 - ActorD
- * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
+ * @SINCE_1_0.0
* @param[in] itemId The Item ID of the item to remove.
* @param[in] durationSeconds How long the relayout takes in seconds.
+ * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
*/
void RemoveItem(ItemId itemId, float durationSeconds);
/**
* @brief Remove a set of items; this is more efficient than calling RemoveItem() repeatedly.
*
- * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
+ * @SINCE_1_0.0
* @param[in] itemIds The IDs of the items to remove.
* @param[in] durationSeconds How long the relayout takes in seconds.
+ * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
*/
void RemoveItems(const ItemIdContainer& itemIds, float durationSeconds);
* @brief Replace an item.
*
* A relayout will occur for the replacement item only.
- * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
+ * @SINCE_1_0.0
* @param[in] replacementItem The replacement for an existing item.
* @param[in] durationSeconds How long the relayout takes in seconds.
+ * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
*/
void ReplaceItem(Item replacementItem, float durationSeconds);
* @brief Replace a set of items.
*
* A relayout will occur for the replacement items only.
- * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
+ * @SINCE_1_0.0
* @param[in] replacementItems The replacements for a set of existing items.
* @param[in] durationSeconds How long the relayout takes in seconds.
+ * @pre durationSeconds must be zero or greater; zero means the relayout occurs instantly.
*/
void ReplaceItems(const ItemContainer& replacementItems, float durationSeconds);
/**
- * @brief Set the parent origin of the items
+ * @brief Set the parent origin of the items.
*
* A relayout will occur for all the items if the parent origin is different than the current one.
+ * @SINCE_1_0.0
* @param[in] parentOrigin New parent origin position vector
*/
void SetItemsParentOrigin( const Vector3& parentOrigin );
/**
- * @brief Get the parent origin of the items
+ * @brief Get the parent origin of the items.
*
+ * @SINCE_1_0.0
* @return The current parent origin of the items
*/
Vector3 GetItemsParentOrigin() const;
/**
- * @brief Set the anchor point of the items
+ * @brief Set the anchor point of the items.
*
* A relayout will occur for all the items if the anchor point is different than the current one.
+ * @SINCE_1_0.0
* @param[in] anchorPoint New anchor point position vector
*/
void SetItemsAnchorPoint( const Vector3& anchorPoint );
/**
- * @brief Get the anchor point of the items
+ * @brief Get the anchor point of the items.
*
+ * @SINCE_1_0.0
* @return The current anchor point of the items
*/
Vector3 GetItemsAnchorPoint() const;
/**
* @brief Get the range of items that are currently in ItemView.
*
+ * @SINCE_1_0.0
* @param[out] range The range of items.
*/
void GetItemsRange(ItemRange& range);
* @code
* void YourCallbackName();
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
ItemView::LayoutActivatedSignalType& LayoutActivatedSignal();
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL ItemView(Internal::ItemView& implementation);
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL ItemView( Dali::Internal::CustomActor* internal );
*/
/**
- * Move Actor constraint.
+ * @brief Move Actor constraint.
*
* Moves an Actor in accordance to scroll position.
+ * @SINCE_1_0.0
*/
DALI_IMPORT_API void MoveActorConstraint( Vector3& current, const PropertyInputContainer& inputs );
/**
- * Wrap Actor constraint.
+ * @brief Wrap Actor constraint.
*
* Wraps an Actors position in accordance to min/max bounds of domain.
+ * @SINCE_1_0.0
*/
DALI_IMPORT_API void WrapActorConstraint( Vector3& position, const PropertyInputContainer& inputs );
* properties that can be used with visual effects. Such as creating
* constraints that are applied to ShaderEffects or Actors using these
* properties as inputs.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API ScrollViewEffect : public Dali::BaseHandle
{
* @brief Create an uninitialized ScrollViewEffect; this can only be initialized with derived classes.
*
* Calling member functions with an uninitialized Toolkit::BaseObject is not allowed.
+ * @SINCE_1_0.0
*/
ScrollViewEffect();
/**
* @brief This constructor is used by Dali New() methods.
*
+ * @SINCE_1_0.0
* @param [in] impl A pointer to a newly allocated Dali resource
*/
explicit DALI_INTERNAL ScrollViewEffect(Internal::ScrollViewEffect *impl);
*/
/**
- * ScrollView Page Path Effect.
+ * @brief ScrollView Page Path Effect.
+ *
* This effect causes Actors to follow a given path. The opacity of the actor will be 0.0 at
* the beginning of the path and will go to 1.0 as it is approximating to half of the path to return
* to 0.0 at the end of the path
*
* Automatic operation:
* not implemented.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API ScrollViewPagePathEffect : public ScrollViewEffect
{
public:
/**
- * Create an initialized ScrollViewPagePathEffect.
+ * @brief Create an initialized ScrollViewPagePathEffect.
+ * @SINCE_1_0.0
* @param[in] path The path that will be used by the scroll effect
* @param[in] forward Vector in page object space which will be aligned with the tangent of the path
* @param[in] inputPropertyIndex Index of a property of the scroll-view which will be used as the input for the path.
static ScrollViewPagePathEffect New(Path path, const Vector3& forward, Dali::Property::Index inputPropertyIndex, const Vector3& pageSize, unsigned int pageCount);
/**
- * Create an uninitialized ScrollViewPagePathEffect; this can be initialized with ScrollViewPagePathEffect::New()
+ * @brief Create an uninitialized ScrollViewPagePathEffect; this can be initialized with ScrollViewPagePathEffect::New()
* Calling member functions with an uninitialized Toolkit::ScrollViewPagePathEffect is not allowed.
+ * @SINCE_1_0.0
*/
ScrollViewPagePathEffect();
/**
- * Downcast an Object handle to ScrollViewPagePathEffect. If handle points to a ScrollViewPagePathEffect the
+ * @brief Downcast a handle to ScrollViewPagePathEffect handle.
+ *
+ * If handle points to a ScrollViewPagePathEffect the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a ScrollViewPagePathEffect or an uninitialized handle
*/
static ScrollViewPagePathEffect DownCast( BaseHandle handle );
/**
- * Manually apply effect to a page in the scroll-view.
+ * @brief Manually apply effect to a page in the scroll-view.
+ * @SINCE_1_0.0
* @param[in] page The page to be affected by this effect.
* @param[in] pageOrder The order of the page in the scroll-view
*/
protected:
/**
- * This constructor is used by Dali New() methods.
+ * @brief This constructor is used by Dali New() methods.
+ * @SINCE_1_0.0
* @param [in] impl A pointer to a newly allocated Dali resource
*/
explicit DALI_INTERNAL ScrollViewPagePathEffect( Internal::ScrollViewPagePathEffect *impl );
/**
* @brief How axes/rotation or scale are clamped
+ * @SINCE_1_0.0
*/
enum ClampState
{
- NotClamped, ///< The quantity isn't clamped
- ClampedToMin, ///< The quantity is clamped to the min value
- ClampedToMax ///< The quantity is clamped to the max value
+ NotClamped, ///< The quantity isn't clamped @SINCE_1_0.0
+ ClampedToMin, ///< The quantity is clamped to the min value @SINCE_1_0.0
+ ClampedToMax ///< The quantity is clamped to the max value @SINCE_1_0.0
};
/**
* @brief A 2 dimensional clamp
+ * @SINCE_1_0.0
*/
struct ClampState2D
{
/**
* @brief The snap type
+ * @SINCE_1_0.0
*/
enum SnapType
{
- Snap, ///< Snap
- Flick ///< Flick
+ Snap, ///< Snap @SINCE_1_0.0
+ Flick ///< Flick @SINCE_1_0.0
};
/**
* @brief DirectionBias types.
+ * @SINCE_1_0.0
*/
enum DirectionBias
{
- DirectionBiasLeft = -1, ///< Bias scroll snap to Left
- DirectionBiasNone = 0, ///< Don't bias scroll snap
- DirectionBiasRight = 1 ///< Bias scroll snap to Right
+ DirectionBiasLeft = -1, ///< Bias scroll snap to Left @SINCE_1_0.0
+ DirectionBiasNone = 0, ///< Don't bias scroll snap @SINCE_1_0.0
+ DirectionBiasRight = 1 ///< Bias scroll snap to Right @SINCE_1_0.0
};
/**
* @brief Used for specifying minimum/maximum extents of a ruler.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API RulerDomain
{
/**
* @brief Creates Ruler domain allowing a point to traverse between min and max extents.
*
+ * @SINCE_1_0.0
* @param[in] min Minimum extent (point cannot traverse less than this)
* @param[in] max Maximum extent (point cannot traverse greater than this)
* @param[in] enabled Whether domain has been enabled or not.
* An optional length parameter can be specified to suggest that the
* subject is not a point but a line to that should be clamped.
*
+ * @SINCE_1_0.0
* @param[in] x X point to be clamped between (min) and (max) extents.
* @param[in] length (optional) The Length of the line from (x) to (x + length) to be clamped.
* @param[in] scale Scaling parameter which treats domain as scaled in calculations.
* An optional length parameter can be specified to suggest that the
* subject is not a point but a line to that should be clamped.
*
+ * @SINCE_1_0.0
* @param[in] x X point to be clamped between (min) and (max) extents.
* @param[in] length (optional) The Length of the line from (x) to (x + length) to be clamped.
* @param[in] scale Scaling parameter which treats domain as scaled in calculations.
/**
* @brief Returns (max-min) size of ruler.
*
+ * @SINCE_1_0.0
* @return The size of the ruler from min to max.
*/
float GetSize() const;
*
* It can specify whether they are traversable, where their snap
* points are and their domain.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API Ruler : public RefObject
{
public:
/// @brief The type of the ruler
enum RulerType {
- Fixed, ///< A fixed ruler
- Free ///< A free ruler
+ Fixed, ///< A fixed ruler @SINCE_1_0.0
+ Free ///< A free ruler @SINCE_1_0.0
};
public:
/**
* @brief Constructs ruler, default enabled, with limitless domain.
+ * @SINCE_1_0.0
*/
Ruler();
/**
* @brief Snaps (x) in accordance to the ruler settings.
*
+ * @SINCE_1_0.0
* @param[in] x The input value on the ruler to be snapped.
* @param[in] bias (optional) The biasing employed for snapping
* 0 floor input (floor x) "Used for Flick Left"
* number of pages within the domain), while wrapping the position
* within the domain.
*
+ * @SINCE_1_0.0
* @param[in] page The page index
* @param[out] volume The overflow volume when the page exceeds the domain (wrap must be enabled)
* @param[in] wrap Enable wrap mode
*
* If (wrap) is true, then will return a page wrapped within the domain.
*
+ * @SINCE_1_0.0
* @param[in] position The position on the domain
* @param[in] wrap Enable wrap mode
* @return The page where this position resides.
/**
* @brief Returns the total number of pages within this Ruler.
*
+ * @SINCE_1_0.0
* @return The number of pages in the Ruler.
*/
virtual unsigned int GetTotalPages() const = 0;
/**
* @brief Gets the extension interface of the Ruler.
*
+ * @SINCE_1_0.0
* @return The extension interface of the Ruler
*/
virtual RulerExtension* GetExtension() { return NULL; }
/**
* @brief Gets the ruler type.
*
+ * @SINCE_1_0.0
* @return The ruler type.
*/
Ruler::RulerType GetType() const;
/**
* @brief Returns whether this axis has been enabled or not.
*
+ * @SINCE_1_0.0
* @return true if axis is enabled
*/
bool IsEnabled() const;
/**
* @brief Enables ruler (ruler must be enabled in order to traverse along it).
+ * @SINCE_1_0.0
*/
void Enable();
/**
* @brief Disables ruler.
+ * @SINCE_1_0.0
*/
void Disable();
/**
* @brief Sets Domain.
*
+ * @SINCE_1_0.0
* @param[in] domain Ruler domain object.
*/
void SetDomain(RulerDomain domain);
/**
* @brief Gets Domain.
*
+ * @SINCE_1_0.0
* @return The domain
*/
const RulerDomain &GetDomain() const;
/**
* @brief Disables Domain (minimum/maximum extents for this axis).
+ * @SINCE_1_0.0
*/
void DisableDomain();
* An optional length parameter can be specified to suggest that the
* subject is not a point but a line that should be clamped.
*
+ * @SINCE_1_0.0
* @param[in] x X point to be clamped between (min) and (max) extents.
* @param[in] length (optional) The Length of the line from (x) to (x + length) to be clamped.
* @param[in] scale Scaling parameter which treats domain as scaled in calculations.
* An optional length parameter can be specified to suggest that the
* subject is not a point but a line to that should be clamped.
*
+ * @SINCE_1_0.0
* @param[in] x X point to be clamped between (min) and (max) extents.
* @param[in] length (optional) The Length of the line from (x) to (x + length) to be clamped.
* @param[in] scale Scaling parameter which treats domain as scaled in calculations.
/**
* @brief Snaps and Clamps (x) in accordance to ruler settings.
*
+ * @SINCE_1_0.0
* @param[in] x value to be snapped in accordance to ruler snap value,
* and clamped in accordance to the ruler's domain (if set).
* @param[in] bias (optional) The biasing employed for snapping
/**
* @brief Snaps and Clamps (x) in accordance to ruler settings.
*
+ * @SINCE_1_0.0
* @param[in] x value to be snapped in accordance to ruler snap value,
* and clamped in accordance to the ruler's domain (if set).
* @param[in] bias (optional) The biasing employed for snapping
/**
* @brief Destructor - A reference counted object may only be deleted by calling Unreference().
+ * @SINCE_1_0.0
*/
virtual ~Ruler();
};
-typedef IntrusivePtr<Ruler> RulerPtr; ///< Pointer to Dali::Toolkit::Ruler object
+typedef IntrusivePtr<Ruler> RulerPtr; ///< Pointer to Dali::Toolkit::Ruler object @SINCE_1_0.0
/**
* @brief Concrete implementation of Ruler that has no snapping and has one single page.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API DefaultRuler : public Ruler
{
public:
/**
* @brief DefaultRuler constructor.
+ * @SINCE_1_0.0
*/
DefaultRuler();
/**
* @brief Concrete implementation of Ruler that has fixed snapping.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API FixedRuler : public Ruler
{
/**
* @brief Constructor
*
+ * @SINCE_1_0.0
* @param[in] spacing The spacing between each interval on this ruler.
*/
FixedRuler(float spacing = 1.0f);
* | %Signal Name | Method |
* |-------------------|----------------------------|
* | snap-started | @ref SnapStartedSignal() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API ScrollView : public Scrollable
{
/**
* @brief Clamp signal event's data
+ * @SINCE_1_0.0
*/
struct ClampEvent
{
/**
* @brief Snap signal event's data.
+ * @SINCE_1_0.0
*/
struct SnapEvent
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
+ PROPERTY_START_INDEX = Toolkit::Scrollable::PROPERTY_END_INDEX + 1, ///< @SINCE_1_1.18
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices, @SINCE_1_1.18
+
ANIMATABLE_PROPERTY_START_INDEX = Toolkit::Scrollable::ANIMATABLE_PROPERTY_END_INDEX + 1,
- ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_START_INDEX + 1000 ///< Reserve animatable property indices
+ ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_START_INDEX + 1000 ///< Reserve animatable property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the ScrollView class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- SCROLL_POSITION = ANIMATABLE_PROPERTY_START_INDEX, ///< Property, name "scrollPosition", type Vector2
- SCROLL_PRE_POSITION, ///< Property, name "scrollPrePosition", type Vector2
- SCROLL_PRE_POSITION_X, ///< Property, name "scrollPrePositionX", type float
- SCROLL_PRE_POSITION_Y, ///< Property, name "scrollPrePositionY", type float
- SCROLL_PRE_POSITION_MAX, ///< Property, name "scrollPrePositionMax", type Vector2
- SCROLL_PRE_POSITION_MAX_X, ///< Property, name "scrollPrePositionMaxX", type float
- SCROLL_PRE_POSITION_MAX_Y, ///< Property, name "scrollPrePositionMaxY", type float
- OVERSHOOT_X, ///< Property, name "overshootX", type float
- OVERSHOOT_Y, ///< Property, name "overshootY", type float
- SCROLL_FINAL, ///< Property, name "scrollFinal", type Vector2
- SCROLL_FINAL_X, ///< Property, name "scrollFinalX", type float
- SCROLL_FINAL_Y, ///< Property, name "scrollFinalY", type float
- WRAP, ///< Property, name "wrap", type bool
- PANNING, ///< Property, name "panning", type bool
- SCROLLING, ///< Property, name "scrolling", type bool
- SCROLL_DOMAIN_SIZE, ///< Property, name "scrollDomainSize", type Vector2
- SCROLL_DOMAIN_SIZE_X, ///< Property, name "scrollDomainSizeX", type float
- SCROLL_DOMAIN_SIZE_Y, ///< Property, name "scrollDomainSizeY", type float
- SCROLL_DOMAIN_OFFSET, ///< Property, name "scrollDomainOffset", type Vector2
- SCROLL_POSITION_DELTA, ///< Property, name "scrollPositionDelta", type Vector2
- START_PAGE_POSITION ///< Property, name "startPagePosition", type Vector3
+ // Event side properties
+ WRAP_ENABLED = PROPERTY_START_INDEX, ///< Property, name "wrapEnabled", @see SetWrapMode(), type bool, @SINCE_1_1.18
+ PANNING_ENABLED, ///< Property, name "panningEnabled", @see SetScrollSensitive(), type bool, @SINCE_1_1.18
+ AXIS_AUTO_LOCK_ENABLED, ///< Property, name "axisAutoLockEnabled", @see SetAxisAutoLock(), type bool, @SINCE_1_1.18
+ WHEEL_SCROLL_DISTANCE_STEP, ///< Property, name "wheelScrollDistanceStep", @see SetWheelScrollDistanceStep(), type Vector2, @SINCE_1_1.18
+
+ SCROLL_POSITION = ANIMATABLE_PROPERTY_START_INDEX, ///< Property, name "scrollPosition", type Vector2 @SINCE_1_0.0
+ SCROLL_PRE_POSITION, ///< Property, name "scrollPrePosition", type Vector2 @SINCE_1_0.0
+ SCROLL_PRE_POSITION_X, ///< Property, name "scrollPrePositionX", type float @SINCE_1_0.0
+ SCROLL_PRE_POSITION_Y, ///< Property, name "scrollPrePositionY", type float @SINCE_1_0.0
+ SCROLL_PRE_POSITION_MAX, ///< Property, name "scrollPrePositionMax", type Vector2 @SINCE_1_0.0
+ SCROLL_PRE_POSITION_MAX_X, ///< Property, name "scrollPrePositionMaxX", type float @SINCE_1_0.0
+ SCROLL_PRE_POSITION_MAX_Y, ///< Property, name "scrollPrePositionMaxY", type float @SINCE_1_0.0
+ OVERSHOOT_X, ///< Property, name "overshootX", type float @SINCE_1_0.0
+ OVERSHOOT_Y, ///< Property, name "overshootY", type float @SINCE_1_0.0
+ SCROLL_FINAL, ///< Property, name "scrollFinal", type Vector2 @SINCE_1_0.0
+ SCROLL_FINAL_X, ///< Property, name "scrollFinalX", type float @SINCE_1_0.0
+ SCROLL_FINAL_Y, ///< Property, name "scrollFinalY", type float @SINCE_1_0.0
+ WRAP, ///< Property, name "wrap", type bool @SINCE_1_0.0
+ PANNING, ///< Property, name "panning", type bool @SINCE_1_0.0
+ SCROLLING, ///< Property, name "scrolling", type bool @SINCE_1_0.0
+ SCROLL_DOMAIN_SIZE, ///< Property, name "scrollDomainSize", type Vector2 @SINCE_1_0.0
+ SCROLL_DOMAIN_SIZE_X, ///< Property, name "scrollDomainSizeX", type float @SINCE_1_0.0
+ SCROLL_DOMAIN_SIZE_Y, ///< Property, name "scrollDomainSizeY", type float @SINCE_1_0.0
+ SCROLL_DOMAIN_OFFSET, ///< Property, name "scrollDomainOffset", type Vector2 @SINCE_1_0.0
+ SCROLL_POSITION_DELTA, ///< Property, name "scrollPositionDelta", type Vector2 @SINCE_1_0.0
+ START_PAGE_POSITION ///< Property, name "startPagePosition", type Vector3 @SINCE_1_0.0
};
};
// Typedefs
- typedef Signal< void ( const SnapEvent& ) > SnapStartedSignalType; ///< SnapStarted signal type
+ typedef Signal< void ( const SnapEvent& ) > SnapStartedSignalType; ///< SnapStarted signal type @SINCE_1_0.0
public:
/**
* @brief Creates an empty ScrollView handle.
+ * @SINCE_1_0.0
*/
ScrollView();
/**
* @brief Copy constructor.
*
- * Creates another handle that points to the same real object
+ * Creates another handle that points to the same real object.
*
+ * @SINCE_1_0.0
* @param[in] handle to copy from
*/
ScrollView( const ScrollView& handle );
/**
* @brief Assignment operator.
*
- * Changes this handle to point to another real object
+ * Changes this handle to point to another real object.
+ * @SINCE_1_0.0
* @param[in] handle The handle to copy from
* @return A reference to this
*/
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~ScrollView();
/**
* @brief Create an initialized ScrollView.
*
+ * @SINCE_1_0.0
* @return A handle to a newly allocated Dali resource.
*/
static ScrollView New();
/**
- * @brief Downcast an Object handle to ScrollView.
+ * @brief Downcast a handle to ScrollView handle.
*
* If handle points to a ScrollView the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a ScrollView or an uninitialized handle
+ * @return A handle to a ScrollView or an uninitialized handle
*/
static ScrollView DownCast( BaseHandle handle );
/**
* @brief Get snap-animation's AlphaFunction.
*
+ * @SINCE_1_0.0
* @return Current easing alpha function of the snap animation.
*/
AlphaFunction GetScrollSnapAlphaFunction() const;
/**
* @brief Set snap-animation's AlphaFunction.
*
+ * @SINCE_1_0.0
* @param[in] alpha Easing alpha function of the snap animation.
*/
void SetScrollSnapAlphaFunction(AlphaFunction alpha);
/**
* @brief Get flick-animation's AlphaFunction.
*
+ * @SINCE_1_0.0
* @return Current easing alpha function of the flick animation.
*/
AlphaFunction GetScrollFlickAlphaFunction() const;
/**
* @brief Set flick-animation's AlphaFunction.
*
+ * @SINCE_1_0.0
* @param[in] alpha Easing alpha function of the flick animation.
*/
void SetScrollFlickAlphaFunction(AlphaFunction alpha);
*
* This animation occurs when the user drags, and releases.
*
+ * @SINCE_1_0.0
* @return The time in seconds for the animation to take.
*/
float GetScrollSnapDuration() const;
*
* This animation occurs when the user drags, and releases.
*
+ * @SINCE_1_0.0
* @param[in] time The time in seconds for the animation to take.
*/
void SetScrollSnapDuration(float time);
*
* This animation occurs when the user flicks scroll view.
*
+ * @SINCE_1_0.0
* @return The time in seconds for the animation to take.
*/
float GetScrollFlickDuration() const;
*
* This animation occurs when the user flicks scroll view.
*
+ * @SINCE_1_0.0
* @param[in] time The time in seconds for the animation to take.
*/
void SetScrollFlickDuration(float time);
* Defines how scrolling horizontally is snapped, and
* the boundary (domain) in which the ScrollView can pan.
*
+ * @SINCE_1_0.0
* @param[in] ruler The ruler to be used for the X axis
*/
void SetRulerX(RulerPtr ruler);
* Defines how scrolling vertically is snapped, and the boundary
* (domain) in which the ScrollView can pan.
*
+ * @SINCE_1_0.0
* @param[in] ruler The ruler to be used for the Y axis
*/
void SetRulerY(RulerPtr ruler);
/**
- * @brief Set Scroll's touch sensitivity.
+ * @brief Set scroll sensibility of pan gesture.
*
- * @note Unlike SetSensitive(), this determines whether this ScrollView
+ * @SINCE_1_0.0
+ * @param[in] sensitive true to enable scroll, false to disable scrolling
+ * @note Unlike Actor::SetSensitive(), this determines whether this ScrollView
* should react (e.g. pan), without disrupting the sensitivity of it's children.
*
- * @param[in] sensitive true to enable scroll, false to disable scrolling
*/
void SetScrollSensitive(bool sensitive);
* The final overshoot value is within 0.0f to 1.0f, but the maximum
* overshoot is in pixels (e.g. if you scroll 75 pixels beyond the
* edge of a scrollable area and the maximum overshoot is 100 then
- * the final overshoot value will be 0.75f)
+ * the final overshoot value will be 0.75f).
*
- * @param[in] overshootX the maximum number of horizontally scrolled pixels before overshoot X reaches 1.0f
- * @param[in] overshootY the maximum number of vertically scrolled pixels before overshoot Y reaches 1.0f
+ * @SINCE_1_0.0
+ * @param[in] overshootX The maximum number of horizontally scrolled pixels before overshoot X reaches 1.0f
+ * @param[in] overshootY The maximum number of vertically scrolled pixels before overshoot Y reaches 1.0f
*/
void SetMaxOvershoot(float overshootX, float overshootY);
/**
* @brief Set Snap Overshoot animation's AlphaFunction.
*
+ * @SINCE_1_0.0
* @param[in] alpha Easing alpha function of the overshoot snap animation.
*/
void SetSnapOvershootAlphaFunction(AlphaFunction alpha);
/**
* @brief Set Snap Overshoot animation's Duration.
*
+ * @SINCE_1_0.0
+ * @param[in] duration The duration of the overshoot snap animation.
* @note Set duration to 0 seconds, to disable Animation.
*
- * @param[in] duration The duration of the overshoot snap animation.
*/
void SetSnapOvershootDuration(float duration);
* snap to the closest actor (The closest actor will appear in the center of
* the ScrollView).
*
+ * @SINCE_1_0.0
* @param[in] enable Enables (true), or disables (false) Actor AutoSnap
*/
void SetActorAutoSnap(bool enable);
*
* When enabled, the ScrollView contents are wrapped over the X/Y Domain.
*
+ * @SINCE_1_0.0
+ * @param[in] enable Enables (true), or disables (false) Wrap Mode.
* @note You must apply a position constraint that causes Wrapping
* to all children.
*
- * @param[in] enable Enables (true), or disables (false) Wrap Mode.
*/
void SetWrapMode(bool enable);
/**
- * @brief Gets the current distance needed to scroll for ScrollUpdatedSignal to be emitted
+ * @brief Gets the current distance needed to scroll for ScrollUpdatedSignal to be emitted.
*
+ * @SINCE_1_0.0
* @return Current scroll update distance
*/
int GetScrollUpdateDistance() const;
/**
- * @brief Sets the distance needed to scroll for ScrollUpdatedSignal to be emitted
+ * @brief Sets the distance needed to scroll for ScrollUpdatedSignal to be emitted.
*
* The scroll update distance tells ScrollView how far to move before ScrollUpdatedSignal the informs application.
- * Each time the ScrollView crosses this distance the signal will be emitted
+ * Each time the ScrollView crosses this distance the signal will be emitted.
*
+ * @SINCE_1_0.0
* @param[in] distance The distance for ScrollView to move before emitting update signal
*/
void SetScrollUpdateDistance(int distance);
/**
* @brief Returns state of Axis Auto Lock mode.
*
+ * @SINCE_1_0.0
* @return Whether Axis Auto Lock mode has been enabled or not.
*/
bool GetAxisAutoLock() const;
* vertical, will be automatically restricted to horizontal only or vertical
* only panning, until the pan gesture has completed.
*
+ * @SINCE_1_0.0
* @param[in] enable Enables (true), or disables (false) AxisAutoLock mode.
*/
void SetAxisAutoLock(bool enable);
* @brief Gets the gradient threshold at which a panning gesture
* should be locked to the Horizontal or Vertical axis.
*
+ * @SINCE_1_0.0
* @return The gradient, a value between 0.0 and 1.0f.
*/
float GetAxisAutoLockGradient() const;
* By default this is 0.36 (0.36:1) which means angles less than 20
* degrees to an axis will lock to that axis.
*
- * @note: Specifying a value of 1.0 (the maximum value accepted) indicates that
+ * @SINCE_1_0.0
+ * @param[in] gradient A value between 0.0 and 1.0 (auto-lock for all angles)
+ * @note Specifying a value of 1.0 (the maximum value accepted) indicates that
* all panning gestures will auto-lock. Either to the horizontal or vertical axis.
*
- * @param[in] gradient A value between 0.0 and 1.0 (auto-lock for all angles)
*/
void SetAxisAutoLockGradient(float gradient);
*
* This is a value in stage-diagonals per second^2.
* stage-diagonal = Length( stage.width, stage.height )
+ * @SINCE_1_0.0
* @return Friction coefficient is returned.
*/
float GetFrictionCoefficient() const;
* A stage 480x800 in size has a diagonal length of 933.
* Friction coefficient of 1.0 means the swipe velocity will
* reduce by 1.0 * 933 pixels/sec^2.
+ * @SINCE_1_0.0
* @param[in] friction Friction coefficient, must be greater than 0.0 (default = 1.0)
*/
void SetFrictionCoefficient(float friction);
* This is a constant which multiplies the input touch
* flick velocity to determine the actual velocity at
* which to move the scrolling area.
+ * @SINCE_1_0.0
* @return The flick speed coefficient is returned.
*/
float GetFlickSpeedCoefficient() const;
* This is a constant which multiplies the input touch
* flick velocity to determine the actual velocity at
* which to move the scrolling area.
+ * @SINCE_1_0.0
* @param[in] speed The flick speed coefficient (default = 1.0).
*/
void SetFlickSpeedCoefficient(float speed);
/**
- * @brief Returns the minimum pan distance required for a flick gesture in pixels
+ * @brief Returns the minimum pan distance required for a flick gesture in pixels.
*
+ * @SINCE_1_0.0
* @return Minimum pan distance vector with separate x and y distance
*/
Vector2 GetMinimumDistanceForFlick() const;
/**
- * @brief Sets the minimum pan distance required for a flick in pixels
+ * @brief Sets the minimum pan distance required for a flick in pixels.
*
- * Takes a Vector2 containing separate x and y values. As long as the pan distance exceeds one of these axes a flick will be allowed
+ * Takes a Vector2 containing separate x and y values. As long as the pan distance exceeds one of these axes a flick will be allowed.
*
+ * @SINCE_1_0.0
* @param[in] distance The minimum pan distance for a flick
*/
void SetMinimumDistanceForFlick( const Vector2& distance );
/**
- * @brief Returns the minimum pan speed required for a flick gesture in pixels per second
+ * @brief Returns the minimum pan speed required for a flick gesture in pixels per second.
*
+ * @SINCE_1_0.0
* @return Minimum pan speed
*/
float GetMinimumSpeedForFlick() const;
/**
- * @brief Sets the minimum pan speed required for a flick in pixels per second
+ * @brief Sets the minimum pan speed required for a flick in pixels per second.
*
+ * @SINCE_1_0.0
* @param[in] speed The minimum pan speed for a flick
*/
void SetMinimumSpeedForFlick( float speed );
*
* This is a value in stage-diagonals per second.
* stage-diagonal = Length( stage.width, stage.height )
+ * @SINCE_1_0.0
* @return Maximum flick speed is returned
*/
float GetMaxFlickSpeed() const;
* A stage 480x800 in size has a diagonal length of 933.
* Max Flick speed of 1.0 means the maximum velocity of
* a swipe can be 1.0 * 933 pixels/sec.
+ * @SINCE_1_0.0
* @param[in] speed Maximum flick speed (default = 3.0)
*/
void SetMaxFlickSpeed(float speed);
* @brief Gets the step of scroll distance in actor coordinates for
* each wheel event received in free panning mode.
*
+ * @SINCE_1_0.0
* @return The step of scroll distance(pixel) in X and Y axes.
*/
Vector2 GetWheelScrollDistanceStep() const;
* @brief Sets the step of scroll distance in actor coordinates for
* each wheel event received in free panning mode.
*
+ * @SINCE_1_0.0
* @param[in] step The step of scroll distance(pixel) in X and Y axes.
*
- * @note: If snap points are defined in the rulers, it will always
+ * @note If snap points are defined in the rulers, it will always
* scroll to the next snap point towards the scroll direction while
* receiving the wheel events.
*
* @brief Retrieves current scroll position.
*
* @returns The current scroll position.
+ * @SINCE_1_0.0
*/
Vector2 GetCurrentScrollPosition() const;
* a grid fashion, increasing from left to right until the end of
* the X-domain.
*
- * @note: Pages start from 0 as the first page, not 1.
+ * @SINCE_1_0.0
+ * @note Pages start from 0 as the first page, not 1.
*
* @returns The Current page.
*/
* increasing Y scrolls contents up.
* - If Rulers have been applied to the axes, then the contents will scroll until
* reaching the domain boundary.
+ * @SINCE_1_0.0
+ * @param[in] position The position to scroll to.
* @note Contents will not snap to ruler snap points.
*
- * @param[in] position The position to scroll to.
*/
void ScrollTo(const Vector2& position);
* increasing Y scrolls contents up.
* - If Rulers have been applied to the axes, then the contents will scroll until
* reaching the domain boundary.
- * @note Contents will not snap to ruler snap points.
- *
+ * @SINCE_1_0.0
* @param[in] position The position to scroll to.
* @param[in] duration The duration of the animation in seconds
+ * @note Contents will not snap to ruler snap points.
+ *
*/
void ScrollTo(const Vector2& position, float duration);
/**
- * @brief Scrolls View to position specified (contents will scroll to this position)
+ * @brief Scrolls View to position specified (contents will scroll to this position).
*
* Position 0,0 is the origin. Increasing X scrolls contents left, while
* increasing Y scrolls contents up.
* - If Rulers have been applied to the axes, then the contents will scroll until
* reaching the domain boundary.
- * @note Contents will not snap to ruler snap points.
- *
+ * @SINCE_1_0.0
* @param[in] position The position to scroll to.
* @param[in] duration The duration of the animation in seconds
* @param[in] alpha The alpha function to use
+ * @note Contents will not snap to ruler snap points.
+ *
*/
void ScrollTo(const Vector2& position, float duration, AlphaFunction alpha);
* increasing Y scrolls contents up.
* - If Rulers have been applied to the axes, then the contents will scroll until
* reaching the domain boundary.
- * @note Contents will not snap to ruler snap points.
- * Biasing parameters are provided such that in scenarios with 2 or 2x2 pages in
- * wrap mode, the application developer can decide whether to scroll left or right
- * to get to the target page
- *
+ * @SINCE_1_0.0
* @param[in] position The position to scroll to.
* @param[in] duration The duration of the animation in seconds
* @param[in] horizontalBias Whether to bias scrolling to left or right.
* @param[in] verticalBias Whether to bias scrolling to top or bottom.
+ * @note Contents will not snap to ruler snap points.
+ * Biasing parameters are provided such that in scenarios with 2 or 2x2 pages in
+ * wrap mode, the application developer can decide whether to scroll left or right
+ * to get to the target page.
+ *
*/
void ScrollTo(const Vector2& position, float duration,
DirectionBias horizontalBias, DirectionBias verticalBias);
/**
- * @brief Scrolls View to position specified (contents will scroll to this position)
+ * @brief Scrolls View to position specified (contents will scroll to this position).
*
* Position 0,0 is the origin. Increasing X scrolls contents left, while
* increasing Y scrolls contents up.
* - If Rulers have been applied to the axes, then the contents will scroll until
* reaching the domain boundary.
- * @note Contents will not snap to ruler snap points.
- * Biasing parameters are provided such that in scenarios with 2 or 2x2 pages in
- * wrap mode, the application developer can decide whether to scroll left or right
- * to get to the target page
- *
+ * @SINCE_1_0.0
* @param[in] position The position to scroll to.
* @param[in] duration The duration of the animation in seconds
* @param[in] horizontalBias Whether to bias scrolling to left or right.
* @param[in] verticalBias Whether to bias scrolling to top or bottom.
* @param[in] alpha Alpha function to use
+ * @note Contents will not snap to ruler snap points.
+ * Biasing parameters are provided such that in scenarios with 2 or 2x2 pages in
+ * wrap mode, the application developer can decide whether to scroll left or right
+ * to get to the target page.
+ *
*/
void ScrollTo(const Vector2& position, float duration, AlphaFunction alpha,
DirectionBias horizontalBias, DirectionBias verticalBias);
* @brief Scrolls View to page currently based on assumption that each page is
* "(page) * ScrollViewSize.width, 0".
*
+ * @SINCE_1_0.0
+ * @param[in] page to scroll to
* @note Should probably be upgraded so that page is an abstract class, that can be
* a function of ScrollViewSize, ruler domain, ruler snap points etc. as pages may be
* orchestrated in a 2D grid fashion, or variable width.
*
- * @param[in] page to scroll to
*/
void ScrollTo(unsigned int page);
* @brief Scrolls View to page currently based on assumption that each page is
* "(page) * ScrollViewSize.width, 0".
*
+ * @SINCE_1_0.0
+ * @param[in] page to scroll to
+ * @param[in] duration The duration of the animation in seconds
* @note Should probably be upgraded so that page is an abstract class, that can be
* a function of ScrollViewSize, ruler domain, ruler snap points etc. as pages may be
* orchestrated in a 2D grid fashion, or variable width.
*
- * @param[in] page to scroll to
- * @param[in] duration The duration of the animation in seconds
*/
void ScrollTo(unsigned int page, float duration);
* @brief Scrolls View to page currently based on assumption that each page is
* "(page) * ScrollViewSize.width, 0".
*
+ * @SINCE_1_0.0
+ * @param[in] page to scroll to
+ * @param[in] duration The duration of the animation in seconds
+ * @param[in] bias Whether to bias scrolling to left or right.
* @note Should probably be upgraded so that page is an abstract class, that can be
* a function of ScrollViewSize, ruler domain, ruler snap points etc. as pages may be
* orchestrated in a 2D grid fashion, or variable width.
* the application developer can decide whether to scroll left or right to get to
* the target page.
*
- * @param[in] page to scroll to
- * @param[in] duration The duration of the animation in seconds
- * @param[in] bias Whether to bias scrolling to left or right.
*/
void ScrollTo(unsigned int page, float duration, DirectionBias bias);
/**
* @brief Scrolls View such that actor appears in the center of the ScrollView.
*
+ * @SINCE_1_0.0
+ * @param[in] actor The actor to center in on (via Scrolling).
* @note Actor must be a direct child of ScrollView, otherwise will
* cause an assertion failure.
- * @param[in] actor The actor to center in on (via Scrolling).
*/
void ScrollTo(Actor& actor);
/**
* @brief Scrolls View such that actor appears in the center of the ScrollView.
*
- * @note Actor must be a direct child of ScrollView, otherwise will
- * cause an assertion failure.
+ * @SINCE_1_0.0
* @param[in] actor The actor to center in on (via Scrolling).
* @param[in] duration The duration of the animation in seconds
+ * @note Actor must be a direct child of ScrollView, otherwise will
+ * cause an assertion failure.
*/
void ScrollTo(Actor& actor, float duration);
*
* If already at snap points, then will return false, and not scroll.
*
+ * @SINCE_1_0.0
* @return True if Snapping necessary.
*/
bool ScrollToSnapPoint();
/**
* @brief Applies a constraint that will affect the children of ScrollView.
*
- * @note this affects all existing and future Actors that are added to scrollview.
+ * @SINCE_1_0.0
* @param[in] constraint The constraint to apply
+ * @note This affects all existing and future Actors that are added to scrollview.
*/
void ApplyConstraintToChildren(Constraint constraint);
/**
* @brief Removes all constraints that will affect the children of ScrollView.
*
- * @note this removes all constraints from actors that have been added
+ * @SINCE_1_0.0
+ * @note This removes all constraints from actors that have been added
* to scrollview.
*/
void RemoveConstraintsFromChildren();
/**
* @brief Apply Effect to ScrollView.
*
+ * @SINCE_1_0.0
* @param[in] effect The effect to apply to scroll view
*/
void ApplyEffect(ScrollViewEffect effect);
/**
* @brief Remove Effect from ScrollView.
*
+ * @SINCE_1_0.0
* @param[in] effect The effect to remove.
*/
void RemoveEffect(ScrollViewEffect effect);
/**
* @brief Remove All Effects from ScrollView.
+ * @SINCE_1_0.0
*/
void RemoveAllEffects();
* Once an actor is bound to a ScrollView, it will be subject to
* that ScrollView's properties.
*
+ * @SINCE_1_0.0
* @param[in] child The actor to add to this ScrollView.
*/
void BindActor(Actor child);
* @brief Unbind Actor from this ScrollView.
*
* Once Unbound, this ScrollView will not affect the actor.
- * @note this does not remove the child from the ScrollView container
- *
+ * @SINCE_1_0.0
* @param[in] child The actor to be unbound.
+ * @note This does not remove the child from the ScrollView container
+ *
*/
void UnbindActor(Actor child);
/**
* @brief Allows the user to constrain the scroll view in a particular direction.
*
+ * @SINCE_1_0.0
* @param[in] direction The axis to constrain the scroll-view to.
* Usually set to PanGestureDetector::DIRECTION_VERTICAL or PanGestureDetector::DIRECTION_HORIZONTAL (but can be any other angle if desired).
* @param[in] threshold The threshold to apply around the axis.
/**
* @brief Remove a direction constraint from the scroll view.
*
+ * @SINCE_1_0.0
* @param[in] direction The axis to stop constraining to.
* Usually will be PanGestureDetector::DIRECTION_VERTICAL or PanGestureDetector::DIRECTION_HORIZONTAL (but can be any other angle if desired).
*/
/**
* @brief Signal emitted when the ScrollView has started to snap or flick (it tells the target
- * position, scale, rotation for the snap or flick)
+ * position, scale, rotation for the snap or flick).
*
* A callback of the following type may be connected:
* @code
* void YourCallbackName(const SnapEvent& event);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
SnapStartedSignalType& SnapStartedSignal();
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL ScrollView(Internal::ScrollView& implementation);
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL ScrollView( Dali::Internal::CustomActor* internal );
* | scrollStarted | @ref ScrollStartedSignal() |
* | scrollCompleted | @ref ScrollUpdatedSignal() |
* | scrollUpdated | @ref ScrollCompletedSignal() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API Scrollable : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000, ///< Reserve property indices @SINCE_1_0.0
ANIMATABLE_PROPERTY_START_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX,
- ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX + 1000 ///< Reserve animatable property indices
+ ANIMATABLE_PROPERTY_END_INDEX = ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX + 1000 ///< Reserve animatable property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the Scrollable class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
// Event side properties
- OVERSHOOT_EFFECT_COLOR = PROPERTY_START_INDEX, ///< Property, name "overshootEffectColor", @see SetOvershootEffectColor(), type Vector4
- OVERSHOOT_ANIMATION_SPEED, ///< Property, name "overshootAnimationSpeed", @see SetOvershootAnimationSpeed(), type float
+ OVERSHOOT_EFFECT_COLOR = PROPERTY_START_INDEX, ///< Property, name "overshootEffectColor", @see SetOvershootEffectColor(), type Vector4 @SINCE_1_0.0
+ OVERSHOOT_ANIMATION_SPEED, ///< Property, name "overshootAnimationSpeed", @see SetOvershootAnimationSpeed(), type float @SINCE_1_0.0
+ OVERSHOOT_ENABLED, ///< Property, name "overshootEnabled", @see SetOvershootEnabled(), type bool, @SINCE_1_1.18
// Animatable properties
- SCROLL_RELATIVE_POSITION = ANIMATABLE_PROPERTY_START_INDEX, ///< Property, name "scrollRelativePosition", type Vector2
- SCROLL_POSITION_MIN, ///< Property, name "scrollPositionMin", type Vector2
- SCROLL_POSITION_MIN_X, ///< Property, name "scrollPositionMinX", type float
- SCROLL_POSITION_MIN_Y, ///< Property, name "scrollPositionMinY", type float
- SCROLL_POSITION_MAX, ///< Property, name "scrollPositionMax", type Vector2
- SCROLL_POSITION_MAX_X, ///< Property, name "scrollPositionMaxX", type float
- SCROLL_POSITION_MAX_Y, ///< Property, name "scrollPositionMaxY", type float
- CAN_SCROLL_VERTICAL, ///< Property, name "canScrollVertical", type bool
- CAN_SCROLL_HORIZONTAL ///< Property, name "canScrollHorizontal", type bool
+ SCROLL_RELATIVE_POSITION = ANIMATABLE_PROPERTY_START_INDEX, ///< Property, name "scrollRelativePosition", type Vector2 @SINCE_1_0.0
+ SCROLL_POSITION_MIN, ///< Property, name "scrollPositionMin", type Vector2 @SINCE_1_0.0
+ SCROLL_POSITION_MIN_X, ///< Property, name "scrollPositionMinX", type float @SINCE_1_0.0
+ SCROLL_POSITION_MIN_Y, ///< Property, name "scrollPositionMinY", type float @SINCE_1_0.0
+ SCROLL_POSITION_MAX, ///< Property, name "scrollPositionMax", type Vector2 @SINCE_1_0.0
+ SCROLL_POSITION_MAX_X, ///< Property, name "scrollPositionMaxX", type float @SINCE_1_0.0
+ SCROLL_POSITION_MAX_Y, ///< Property, name "scrollPositionMaxY", type float @SINCE_1_0.0
+ CAN_SCROLL_VERTICAL, ///< Property, name "canScrollVertical", type bool @SINCE_1_0.0
+ CAN_SCROLL_HORIZONTAL ///< Property, name "canScrollHorizontal", type bool @SINCE_1_0.0
};
};
// Typedefs
- typedef Signal< void ( const Vector2& ) > ScrollStartedSignalType; ///< ScrollStarted signal type
- typedef Signal< void ( const Vector2& ) > ScrollCompletedSignalType; ///< ScrollCompleted signal type
- typedef Signal< void ( const Vector2& ) > ScrollUpdatedSignalType; ///< Scroll updated signal type
+ typedef Signal< void ( const Vector2& ) > ScrollStartedSignalType; ///< ScrollStarted signal type @SINCE_1_0.0
+ typedef Signal< void ( const Vector2& ) > ScrollCompletedSignalType; ///< ScrollCompleted signal type @SINCE_1_0.0
+ typedef Signal< void ( const Vector2& ) > ScrollUpdatedSignalType; ///< Scroll updated signal type @SINCE_1_0.0
public:
/**
* @brief Creates an uninitialized Scrollable handle.
+ * @SINCE_1_0.0
*/
Scrollable();
/**
* @brief Copy constructor.
*
- * Creates another handle that points to the same real object
+ * Creates another handle that points to the same real object.
*
+ * @SINCE_1_0.0
* @param handle to copy from
*/
Scrollable( const Scrollable& handle );
/**
* @brief Assignment operator.
*
- * Changes this handle to point to another real object
+ * Changes this handle to point to another real object.
+ * @SINCE_1_0.0
* @param[in] handle to copy from
* @return A reference to this
*/
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~Scrollable();
/**
- * @brief Downcast an Object handle to Scrollable.
+ * @brief Downcast a handle to Scrollable handle.
*
* If handle points to a Scrollable the downcast produces valid
* handle. If not the returned handle is left uninitialized.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
- * @return handle to a Scrollable or an uninitialized handle
+ * @return A handle to a Scrollable or an uninitialized handle
*/
static Scrollable DownCast( BaseHandle handle );
/**
* @brief Checks if scroll overshoot has been enabled or not.
*
- * @return Whether the scroll obvershoot is enabled
+ * @SINCE_1_0.0
+ * @return Whether the scroll overshoot is enabled
*/
bool IsOvershootEnabled() const;
/**
* @brief Sets whether to enables or disable scroll overshoot.
*
- * @param[in] enable Whether to enable the scroll obvershoot or not
+ * @SINCE_1_0.0
+ * @param[in] enable Whether to enable the scroll overshoot or not
*/
void SetOvershootEnabled(bool enable);
/**
* @brief Set the color of the overshoot effect.
*
+ * @SINCE_1_0.0
* @param[in] color The color of the overshoot effect.
*/
void SetOvershootEffectColor( const Vector4& color );
/**
* @brief Get the color of the overshoot effect.
+ * @SINCE_1_0.0
* @return The color of the overshoot effect.
*/
Vector4 GetOvershootEffectColor() const;
/**
* @brief Set the speed of overshoot animation in pixels per second.
+ *
* When the speed is not greater than 0, the overshoot is set instantly with no animation.
+ * @SINCE_1_0.0
* @param[in] pixelsPerSecond The speed of the overshoot animation.
*/
void SetOvershootAnimationSpeed( float pixelsPerSecond );
/**
* @brief Get the speed of overshoot animation in pixels per second.
+ * @SINCE_1_0.0
* @return The speed of the overshoot animation.
*/
float GetOvershootAnimationSpeed() const;
* @code
* void YourCallbackName(const Vector2& currentScrollPosition);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
ScrollStartedSignalType& ScrollStartedSignal();
* @code
* void YourCallbackName(const Vector2& currentScrollPosition);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
ScrollUpdatedSignalType& ScrollUpdatedSignal();
* @code
* void YourCallbackName(const Vector2& currentScrollPosition);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
ScrollCompletedSignalType& ScrollCompletedSignal();
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL Scrollable(Internal::Scrollable& implementation);
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL Scrollable( Dali::Internal::CustomActor* internal );
* "cellVerticalAlignment": "center" // property to specify how to align vertically inside the cells, if not set, default value is 'top'
* }
* @endcode
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API TableView : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices @SINCE_1_0.0
};
/**
* It has the format as follows in script:
* @code
* "layoutRows":
- {
- "0": { "policy": "fixed", "value": 40 }, //@see SetFixedHight
- "2": { "policy": "relative", "value": 0.33 }, //@see SetRelativeHeight
- "3": { "policy": "fit", "value":0.0 } //@see SetFitHeight, the value is not used, its height is decided by the children in this row
- }
+ * {
+ * "0": { "policy": "fixed", "value": 40 }, //@see SetFixedHight
+ * "2": { "policy": "relative", "value": 0.33 }, //@see SetRelativeHeight
+ * "3": { "policy": "fit", "value":0.0 } //@see SetFitHeight, the value is not used, its height is decided by the children in this row
+ * }
* @endcode
*
* LayoutColumns: set the height of the rows.
* It has the format as follows in script:
* @code
* "layoutColumns":
- {
- "0": { "policy": "fixed", "value": 40 }, //@see SetFixedWidth
- "1": { "policy": "fit", "value":0.0 } //@see SetFitHeight, the value is not used, its width is decided by the children in this column
- "2": { "policy": "relative", "value": 0.33 } //@see SetRelativeWidth
- }
+ * {
+ * "0": { "policy": "fixed", "value": 40 }, //@see SetFixedWidth
+ * "1": { "policy": "fit", "value":0.0 } //@see SetFitHeight, the value is not used, its width is decided by the children in this column
+ * "2": { "policy": "relative", "value": 0.33 } //@see SetRelativeWidth
+ * }
* @endcode
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- ROWS = PROPERTY_START_INDEX, ///< name "rows", type unsigned int
- COLUMNS, ///< name "columns", type unsigned int
- CELL_PADDING, ///< name "cellPadding", type Vector2
- LAYOUT_ROWS, ///< name "layoutRows", type Map
- LAYOUT_COLUMNS, ///< name "layoutColumns", type Map
+ ROWS = PROPERTY_START_INDEX, ///< name "rows", type unsigned int @SINCE_1_0.0
+ COLUMNS, ///< name "columns", type unsigned int @SINCE_1_0.0
+ CELL_PADDING, ///< name "cellPadding", type Vector2 @SINCE_1_0.0
+ LAYOUT_ROWS, ///< name "layoutRows", type Map @SINCE_1_0.0
+ LAYOUT_COLUMNS, ///< name "layoutColumns", type Map @SINCE_1_0.0
};
};
/**
* @brief Describes how the size of a row / column been set
+ * @SINCE_1_0.0
*/
enum LayoutPolicy
{
- FIXED, ///< Fixed with the given value.
- RELATIVE, ///< Calculated as percentage of the remainder after subtracting Padding and Fixed height/width
- FILL, ///< Default policy, get the remainder of the 100% (after subtracting Fixed, Fit and Relative height/ width) divided evenly between 'fill' rows/columns
- FIT ///< Fit around its children.
+ FIXED, ///< Fixed with the given value. @SINCE_1_0.0
+ RELATIVE, ///< Calculated as percentage of the remainder after subtracting Padding and Fixed height/width @SINCE_1_0.0
+ FILL, ///< Default policy, get the remainder of the 100% (after subtracting Fixed, Fit and Relative height/ width) divided evenly between 'fill' rows/columns @SINCE_1_0.0
+ FIT ///< Fit around its children. @SINCE_1_0.0
};
/**
- * Structure to specify layout position for child actor
+ * @brief Structure to specify layout position for child actor
+ * @SINCE_1_0.0
*/
struct CellPosition
{
/**
- * Constructor to initialise values to defaults for convenience
+ * @brief Constructor to initialise values to defaults for convenience
+ * @SINCE_1_0.0
*/
CellPosition( unsigned int rowIndex = 0, unsigned int columnIndex = 0,
unsigned int rowSpan = 1, unsigned int columnSpan = 1 )
};
/**
- * Create a TableView handle; this can be initialised with TableView::New()
+ * @brief Create a TableView handle; this can be initialised with TableView::New()
* Calling member functions with an uninitialised handle is not allowed.
+ * @SINCE_1_0.0
*/
TableView();
/**
- * Copy constructor. Creates another handle that points to the same real object
+ * @brief Copy constructor. Creates another handle that points to the same real object
+ * @SINCE_1_0.0
* @param handle to copy from
*/
TableView( const TableView& handle );
/**
- * Assignment operator. Changes this handle to point to another real object
+ * @brief Assignment operator. Changes this handle to point to another real object
+ * @SINCE_1_0.0
*/
TableView& operator=( const TableView& handle );
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~TableView();
/**
- * Create the TableView control.
+ * @brief Create the TableView control.
+ * @SINCE_1_0.0
* @param[in] initialRows for the table
* @param[in] initialColumns for the table
* @return A handle to the TableView control.
static TableView New( unsigned int initialRows, unsigned int initialColumns );
/**
- * Downcast an Object handle to TableView. If handle points to a TableView the
+ * @brief Downcast a handle to TableView handle.
+ *
+ * If handle points to a TableView the
* downcast produces valid handle. If not the returned handle is left uninitialized.
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a TableView or an uninitialized handle
*/
static TableView DownCast( BaseHandle handle );
/**
- * Adds a child to the table
+ * @brief Adds a child to the table
* If the row or column index is outside the table, the table gets resized bigger
- * @pre The child actor has been initialized.
+ * @SINCE_1_0.0
* @param[in] child to add
* @param[in] position for the child
* @return true if the addition succeeded, false if the cell is already occupied
+ * @pre The child actor has been initialized.
*/
bool AddChild( Actor child, CellPosition position );
/**
- * Returns a child from the given layout position
- * Note! if there is no child in this position this method returns an uninitialized
- * Actor handle
+ * @brief Returns a child from the given layout position
+ * @SINCE_1_0.0
* @param[in] position in the table
* @return child that was in the cell or an uninitialized handle
+ * @note If there is no child in this position this method returns an uninitialized.
+ * Actor handle
*/
Actor GetChildAt( CellPosition position );
/**
- * Removes a child from the given layout position
- * Note! if there is no child in this position this method does nothing
+ * @brief Removes a child from the given layout position
+ * @SINCE_1_0.0
* @param[in] position for the child to remove
* @return child that was removed or an uninitialized handle
+ * @note If there is no child in this position this method does nothing.
*/
Actor RemoveChildAt( CellPosition position );
/**
- * Finds the childs layout position
+ * @brief Finds the childs layout position
+ * @SINCE_1_0.0
* @param[in] child to search for
* @param[out] position for the child
* @return true if the child was included in this TableView
bool FindChildPosition( Actor child, CellPosition& position );
/**
- * Insert a new row to given index
+ * @brief Insert a new row to given index
+ * @SINCE_1_0.0
* @param [in] rowIndex of the new row
*/
void InsertRow( unsigned int rowIndex );
/**
- * Delete a row from given index
+ * @brief Delete a row from given index
* Removed elements are deleted
+ * @SINCE_1_0.0
* @param [in] rowIndex of the row to delete
*/
void DeleteRow( unsigned int rowIndex );
/**
- * Delete a row from given index
+ * @brief Delete a row from given index
+ * @SINCE_1_0.0
* @param [in] rowIndex of the row to delete
* @param [out] removed elements
*/
void DeleteRow( unsigned int rowIndex, std::vector<Actor>& removed );
/**
- * Insert a new column to given index
+ * @brief Insert a new column to given index
+ * @SINCE_1_0.0
* @param [in] columnIndex of the new column
*/
void InsertColumn( unsigned int columnIndex );
/**
- * Delete a column from given index.
+ * @brief Delete a column from given index.
* Removed elements are deleted
+ * @SINCE_1_0.0
* @param [in] columnIndex of the column to delete
*/
void DeleteColumn( unsigned int columnIndex );
/**
- * Delete a column from given index
+ * @brief Delete a column from given index
+ * @SINCE_1_0.0
* @param [in] columnIndex of the column to delete
* @param [out] removed elements
*/
void DeleteColumn( unsigned int columnIndex, std::vector<Actor>& removed );
/**
- * Resize the TableView. Note! if the new size is smaller than old,
- * superfluous actors get removed. If you want to relayout removed children,
- * use the variant that returns the removed Actors and reinsert them into the table
- * If an actor spans to a removed row or column it gets removed from the table
+ * @brief Resize the TableView.
+ * @SINCE_1_0.0
* @param[in] rows for the table
* @param[in] columns for the table
+ * @note If the new size is smaller than old,
+ * superfluous actors get removed. If you want to relayout removed children,
+ * use the variant that returns the removed Actors and reinsert them into the table.
+ * If an actor spans to a removed row or column it gets removed from the table.
*/
void Resize( unsigned int rows, unsigned int columns );
/**
- * Resize the TableView. Note! if the new size is smaller than old,
- * superfluous actors get removed.
- * If an actor spans to a removed row or column it gets removed from the table
+ * @brief Resize the TableView.
+ * @SINCE_1_0.0
* @param[in] rows for the table
* @param[in] columns for the table
* @param[out] removed actor handles
+ * @note If the new size is smaller than old,
+ * superfluous actors get removed.
+ * If an actor spans to a removed row or column it gets removed from the table.
*/
void Resize( unsigned int rows, unsigned int columns, std::vector<Actor>& removed );
/**
- * Set horizontal and vertical padding between cells
+ * @brief Set horizontal and vertical padding between cells
+ * @SINCE_1_0.0
* @param[in] padding width and height
*/
void SetCellPadding( Size padding );
/**
+ * @brief Get the current padding as width and height.
+ * @SINCE_1_0.0
* @return the current padding as width and height
*/
Size GetCellPadding();
/**
* @brief Specify this row as fitting its height to its children
*
+ * @SINCE_1_0.0
* @param[in] rowIndex The row to set
*/
void SetFitHeight( unsigned int rowIndex );
/**
* @brief Is the row a fit row
*
+ * @SINCE_1_0.0
* @param[in] rowIndex The row to check
* @return Return true if the row is fit
*/
/**
* @brief Specify this column as fitting its width to its children
*
+ * @SINCE_1_0.0
* @param[in] columnIndex The column to set
*/
void SetFitWidth( unsigned int columnIndex );
/**
* @brief Is the column a fit column
*
+ * @SINCE_1_0.0
* @param[in] columnIndex The column to check
* @return Return true if the column is fit
*/
bool IsFitWidth( unsigned int columnIndex ) const;
/**
- * Sets a row to have fixed height
+ * @brief Sets a row to have fixed height
* Setting a fixed height of 0 has no effect
- * @pre The row rowIndex must exist.
+ * @SINCE_1_0.0
* @param rowIndex for row with fixed height
* @param height in world coordinate units
+ * @pre The row rowIndex must exist.
*/
void SetFixedHeight( unsigned int rowIndex, float height );
/**
- * Gets a row's fixed height.
- * Note! The returned value is valid if it has been set before.
- * @pre The row rowIndex must exist.
+ * @brief Gets a row's fixed height.
+ * @SINCE_1_0.0
* @return height in world coordinate units.
+ * @pre The row rowIndex must exist.
+ * @note The returned value is valid if it has been set before.
*/
float GetFixedHeight( unsigned int rowIndex ) const;
/**
- * Sets a row to have relative height. Relative height means percentage of
+ * @brief Sets a row to have relative height. Relative height means percentage of
* the remainder of the table height after subtracting Padding and Fixed height rows
* Setting a relative height of 0 has no effect
- * @pre The row rowIndex must exist.
+ * @SINCE_1_0.0
* @param rowIndex for row with relative height
* @param heightPercentage between 0.0f and 1.0f
+ * @pre The row rowIndex must exist.
*/
void SetRelativeHeight( unsigned int rowIndex, float heightPercentage );
/**
- * Gets a row's relative height.
- * Note! The returned value is valid if it has been set before.
- * @pre The row rowIndex must exist.
+ * @brief Gets a row's relative height.
+ * @SINCE_1_0.0
* @return height in percentage units, between 0.0f and 1.0f.
+ * @pre The row rowIndex must exist.
+ * @note The returned value is valid if it has been set before.
*/
float GetRelativeHeight( unsigned int rowIndex ) const;
/**
- * Sets a column to have fixed width
+ * @brief Sets a column to have fixed width
* Setting a fixed width of 0 has no effect
- * @pre The column columnIndex must exist.
+ * @SINCE_1_0.0
* @param columnIndex for column with fixed width
* @param width in world coordinate units
+ * @pre The column columnIndex must exist.
*/
void SetFixedWidth( unsigned int columnIndex, float width );
/**
- * Gets a column's fixed width.
- * Note! The returned value is valid if it has been set before.
- * @pre The column columnIndex must exist.
+ * @brief Gets a column's fixed width.
+ * @SINCE_1_0.0
* @return width in world coordinate units.
+ * @pre The column columnIndex must exist.
+ * @note The returned value is valid if it has been set before.
*/
float GetFixedWidth( unsigned int columnIndex ) const;
/**
- * Sets a column to have relative width. Relative width means percentage of
+ * @brief Sets a column to have relative width. Relative width means percentage of
* the remainder of table width after subtracting Padding and Fixed width columns
* Setting a relative width of 0 has no effect
- * @pre The column columnIndex must exist.
+ * @SINCE_1_0.0
* @param columnIndex for column with fixed width
* @param widthPercentage between 0.0f and 1.0f
+ * @pre The column columnIndex must exist.
*/
void SetRelativeWidth( unsigned int columnIndex, float widthPercentage );
/**
- * Gets a column's relative width.
- * Note! The returned value is valid if it has been set before.
- * @pre The column columnIndex must exist.
+ * @brief Gets a column's relative width.
+ * @SINCE_1_0.0
* @return width in percentage units, between 0.0f and 1.0f.
+ * @pre The column columnIndex must exist.
+ * @note The returned value is valid if it has been set before.
*/
float GetRelativeWidth( unsigned int columnIndex ) const;
/**
+ * @brief Gets the amount of rows in the table.
+ * @SINCE_1_0.0
* @return the amount of rows in the table
*/
unsigned int GetRows();
/**
+ * @brief Gets the amount of columns in the table.
+ * @SINCE_1_0.0
* @return the amount of columns in the table
*/
unsigned int GetColumns();
*
* Cells without calling this function have the default values of LEFT and TOP respectively.
*
+ * @SINCE_1_0.0
* @param[in] position The cell to set alignment on.
* @param[in] horizontal The horizontal alignment.
* @param[in] vertical The vertical alignment.
public: // Not intended for application developers
/**
- * Creates a handle using the Toolkit::Internal implementation.
+ * @brief Creates a handle using the Toolkit::Internal implementation.
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL TableView(Internal::TableView& implementation);
/**
- * Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL TableView( Dali::Internal::CustomActor* internal );
* | textChanged | @ref TextChangedSignal() |
* | maxLengthReached | @ref MaxLengthReachedSignal() |
*
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API TextField : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices @SINCE_1_0.0
};
/**
- * @brief An enumeration of properties belonging to the TextLabel class.
+ * @brief An enumeration of properties belonging to the TextField class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "renderingBackend", The type or rendering e.g. bitmap-based, type INT
- TEXT, ///< name "text", The text to display in UTF-8 format, type STRING
- PLACEHOLDER_TEXT, ///< name "placeholderText", The text to display when the TextField is empty and inactive, type STRING
- PLACEHOLDER_TEXT_FOCUSED, ///< name "placeholderTextFocused", The text to display when the TextField is empty with key-input focus, type STRING
- FONT_FAMILY, ///< name "fontFamily", The requested font family, type STRING
- FONT_STYLE, ///< name "fontStyle", The requested font style, type STRING
- POINT_SIZE, ///< name "pointSize", The size of font in points, type FLOAT
- MAX_LENGTH, ///< name "maxLength" The maximum number of characters that can be inserted, type INTEGER
- EXCEED_POLICY, ///< name "exceedPolicy" Specifies how the text is truncated when it does not fit, type INTEGER
- HORIZONTAL_ALIGNMENT, ///< name "horizontalAlignment", The line horizontal alignment, type STRING, values "BEGIN", "CENTER", "END"
- VERTICAL_ALIGNMENT, ///< name "verticalAlignment", The line vertical alignment, type STRING, values "TOP", "CENTER", "BOTTOM"
- TEXT_COLOR, ///< name "textColor", The text color, type VECTOR4
- PLACEHOLDER_TEXT_COLOR, ///< name "placeholderTextColor", The placeholder-text color, type VECTOR4
- SHADOW_OFFSET, ///< name "shadowOffset", The drop shadow offset 0 indicates no shadow, type VECTOR2
- SHADOW_COLOR, ///< name "shadowColor", The color of a drop shadow, type VECTOR4
- PRIMARY_CURSOR_COLOR, ///< name "primaryCursorColor", The color to apply to the primary cursor, type VECTOR4
- SECONDARY_CURSOR_COLOR, ///< name "secondaryCursorColor", The color to apply to the secondary cursor, type VECTOR4
- ENABLE_CURSOR_BLINK, ///< name "enableCursorBlink", Whether the cursor should blink or not, type BOOLEAN
- CURSOR_BLINK_INTERVAL, ///< name "cursorBlinkInterval", The time interval in seconds between cursor on/off states, type FLOAT
- CURSOR_BLINK_DURATION, ///< name "cursorBlinkDuration", The cursor will stop blinking after this number of seconds (if non-zero), type FLOAT
- CURSOR_WIDTH, ///< name "cursorWidth", The cursor width, type INTEGER
- GRAB_HANDLE_IMAGE, ///< name "grabHandleImage", The image to display for the grab handle, type STRING
- GRAB_HANDLE_PRESSED_IMAGE, ///< name "grabHandlePressedImage", The image to display when the grab handle is pressed, type STRING
- SCROLL_THRESHOLD, ///< name "scrollThreshold" Scrolling will occur if the cursor is this close to the control border, type FLOAT
- SCROLL_SPEED, ///< name "scrollSpeed" The scroll speed in pixels per second, type FLOAT
- SELECTION_HANDLE_IMAGE_LEFT, ///< name "selectionHandleImageLeft", The image to display for the left selection handle, type MAP
- SELECTION_HANDLE_IMAGE_RIGHT, ///< name "selectionHandleImageRight", The image to display for the right selection handle, type MAP
- SELECTION_HANDLE_PRESSED_IMAGE_LEFT, ///< name "selectionHandlePressedImageLeft", The image to display when the left selection handle is pressed, type MAP
- SELECTION_HANDLE_PRESSED_IMAGE_RIGHT, ///< name "selectionHandlePressedImageRight", The image to display when the right selection handle is pressed, type MAP
- SELECTION_HANDLE_MARKER_IMAGE_LEFT, ///< name "selectionHandleMarkerImageLeft", The image to display for the left selection handle marker, type MAP
- SELECTION_HANDLE_MARKER_IMAGE_RIGHT, ///< name "selectionHandleMarkerImageRight", The image to display for the right selection handle marker, type MAP
- SELECTION_HIGHLIGHT_COLOR, ///< name "selectionHighlightColor", The color of the selection highlight, type VECTOR4
- DECORATION_BOUNDING_BOX, ///< name "decorationBoundingBox", The decorations (handles etc) will positioned within this area on-screen, type RECTANGLE
- INPUT_METHOD_SETTINGS, ///< name "inputMethodSettings", The settings to relating to the System's Input Method, Key and Value type MAP
- INPUT_COLOR, ///< name "inputColor", The color of the new input text, type VECTOR4
- ENABLE_MARKUP ///< name "enableMarkup", Whether the mark-up processing is enabled. type BOOLEAN
+ RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "renderingBackend", The type or rendering e.g. bitmap-based, type INT @SINCE_1_0.0
+ TEXT, ///< name "text", The text to display in UTF-8 format, type STRING @SINCE_1_0.0
+ PLACEHOLDER_TEXT, ///< name "placeholderText", The text to display when the TextField is empty and inactive, type STRING @SINCE_1_0.0
+ PLACEHOLDER_TEXT_FOCUSED, ///< name "placeholderTextFocused", The text to display when the TextField is empty with key-input focus, type STRING @SINCE_1_0.0
+ FONT_FAMILY, ///< name "fontFamily", The requested font family, type STRING @SINCE_1_0.0
+ FONT_STYLE, ///< name "fontStyle", The requested font style, type STRING @SINCE_1_0.0
+ POINT_SIZE, ///< name "pointSize", The size of font in points, type FLOAT @SINCE_1_0.0
+ MAX_LENGTH, ///< name "maxLength" The maximum number of characters that can be inserted, type INTEGER @SINCE_1_0.0
+ EXCEED_POLICY, ///< name "exceedPolicy" Specifies how the text is truncated when it does not fit, type INTEGER @SINCE_1_0.0
+ HORIZONTAL_ALIGNMENT, ///< name "horizontalAlignment", The line horizontal alignment, type STRING, values "BEGIN", "CENTER", "END" @SINCE_1_0.0
+ VERTICAL_ALIGNMENT, ///< name "verticalAlignment", The line vertical alignment, type STRING, values "TOP", "CENTER", "BOTTOM" @SINCE_1_0.0
+ TEXT_COLOR, ///< name "textColor", The text color, type VECTOR4 @SINCE_1_0.0
+ PLACEHOLDER_TEXT_COLOR, ///< name "placeholderTextColor", The placeholder-text color, type VECTOR4 @SINCE_1_0.0
+ SHADOW_OFFSET, ///< name "shadowOffset", The drop shadow offset 0 indicates no shadow, type VECTOR2 @SINCE_1_0.0
+ SHADOW_COLOR, ///< name "shadowColor", The color of a drop shadow, type VECTOR4 @SINCE_1_0.0
+ PRIMARY_CURSOR_COLOR, ///< name "primaryCursorColor", The color to apply to the primary cursor, type VECTOR4 @SINCE_1_0.0
+ SECONDARY_CURSOR_COLOR, ///< name "secondaryCursorColor", The color to apply to the secondary cursor, type VECTOR4 @SINCE_1_0.0
+ ENABLE_CURSOR_BLINK, ///< name "enableCursorBlink", Whether the cursor should blink or not, type BOOLEAN @SINCE_1_0.0
+ CURSOR_BLINK_INTERVAL, ///< name "cursorBlinkInterval", The time interval in seconds between cursor on/off states, type FLOAT @SINCE_1_0.0
+ CURSOR_BLINK_DURATION, ///< name "cursorBlinkDuration", The cursor will stop blinking after this number of seconds (if non-zero), type FLOAT @SINCE_1_0.0
+ CURSOR_WIDTH, ///< name "cursorWidth", The cursor width, type INTEGER @SINCE_1_0.0
+ GRAB_HANDLE_IMAGE, ///< name "grabHandleImage", The image to display for the grab handle, type STRING @SINCE_1_0.0
+ GRAB_HANDLE_PRESSED_IMAGE, ///< name "grabHandlePressedImage", The image to display when the grab handle is pressed, type STRING @SINCE_1_0.0
+ SCROLL_THRESHOLD, ///< name "scrollThreshold" Horizontal scrolling will occur if the cursor is this close to the control border, type FLOAT @SINCE_1_0.0
+ SCROLL_SPEED, ///< name "scrollSpeed" The scroll speed in pixels per second, type FLOAT @SINCE_1_0.0
+ SELECTION_HANDLE_IMAGE_LEFT, ///< name "selectionHandleImageLeft", The image to display for the left selection handle, type MAP @SINCE_1_0.0
+ SELECTION_HANDLE_IMAGE_RIGHT, ///< name "selectionHandleImageRight", The image to display for the right selection handle, type MAP @SINCE_1_0.0
+ SELECTION_HANDLE_PRESSED_IMAGE_LEFT, ///< name "selectionHandlePressedImageLeft", The image to display when the left selection handle is pressed, type MAP @SINCE_1_0.0
+ SELECTION_HANDLE_PRESSED_IMAGE_RIGHT, ///< name "selectionHandlePressedImageRight", The image to display when the right selection handle is pressed, type MAP @SINCE_1_0.0
+ SELECTION_HANDLE_MARKER_IMAGE_LEFT, ///< name "selectionHandleMarkerImageLeft", The image to display for the left selection handle marker, type MAP @SINCE_1_0.0
+ SELECTION_HANDLE_MARKER_IMAGE_RIGHT, ///< name "selectionHandleMarkerImageRight", The image to display for the right selection handle marker, type MAP @SINCE_1_0.0
+ SELECTION_HIGHLIGHT_COLOR, ///< name "selectionHighlightColor", The color of the selection highlight, type VECTOR4 @SINCE_1_0.0
+ DECORATION_BOUNDING_BOX, ///< name "decorationBoundingBox", The decorations (handles etc) will positioned within this area on-screen, type RECTANGLE @SINCE_1_0.0
+ INPUT_METHOD_SETTINGS, ///< name "inputMethodSettings", The settings to relating to the System's Input Method, Key and Value type MAP @SINCE_1_0.0
+ INPUT_COLOR, ///< name "inputColor", The color of the new input text, type VECTOR4 @SINCE_1_0.0
+ ENABLE_MARKUP, ///< name "enableMarkup", Whether the mark-up processing is enabled. type BOOLEAN @SINCE_1_0.0
+ INPUT_FONT_FAMILY, ///< name "inputFontFamily", The font's family of the new input text, type STRING @SINCE_1_0.0
+ INPUT_FONT_STYLE, ///< name "inputFontStyle", The font's style of the new input text, type STRING @SINCE_1_0.0
+ INPUT_POINT_SIZE ///< name "inputPointSize", The font's size of the new input text in points, type FLOAT @SINCE_1_0.0
};
};
* @brief Specifies how the text is truncated when it does not fit
*
* The default value is \e EXCEED_POLICY_CLIP.
+ * @SINCE_1_0.0
*/
enum ExceedPolicy
{
- EXCEED_POLICY_ORIGINAL, ///< The text will be display at original size, and may exceed the TextField boundary.
- EXCEED_POLICY_CLIP ///< The end of text will be clipped to fit within the TextField.
+ EXCEED_POLICY_ORIGINAL, ///< The text will be display at original size, and may exceed the TextField boundary. @SINCE_1_0.0
+ EXCEED_POLICY_CLIP ///< The end of text will be clipped to fit within the TextField. @SINCE_1_0.0
};
// Type Defs
- /// @brief Max Characters Exceed signal type;
+ /// @brief Text changed signal type.
typedef Signal<void ( TextField ) > TextChangedSignalType;
+ /// @brief Max Characters Exceed signal type.
typedef Signal<void ( TextField ) > MaxLengthReachedSignalType;
/**
- * Create the TextField control.
+ * @brief Create the TextField control.
+ * @SINCE_1_0.0
* @return A handle to the TextField control.
*/
static TextField New();
/**
* @brief Creates an empty handle.
+ * @SINCE_1_0.0
*/
TextField();
/**
* @brief Copy constructor.
*
+ * @SINCE_1_0.0
* @param[in] handle The handle to copy from.
*/
TextField( const TextField& handle );
/**
* @brief Assignment operator.
*
+ * @SINCE_1_0.0
* @param[in] handle The handle to copy from.
* @return A reference to this.
*/
TextField& operator=( const TextField& handle );
/**
- * @brief Destructor
+ * @brief Destructor.
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~TextField();
* If the BaseHandle points is a TextField the downcast returns a valid handle.
* If not the returned handle is left empty.
*
- * @param[in] handle Handle to an object
- * @return handle to a TextField or an empty handle
+ * @SINCE_1_0.0
+ * @param[in] handle Handle to an object.
+ * @return handle to a TextField or an empty handle.
*/
static TextField DownCast( BaseHandle handle );
* @code
* void YourCallbackName( TextField textField );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
TextChangedSignalType& TextChangedSignal();
* @code
* void YourCallbackName( TextField textField );
* @endcode
+ * @SINCE_1_0.0
* @return The signal to connect to.
*/
MaxLengthReachedSignalType& MaxLengthReachedSignal();
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL TextField( Internal::TextField& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL TextField( Dali::Internal::CustomActor* internal );
* @brief A control which renders a short text string.
*
* Text labels are lightweight, non-editable and do not respond to user input.
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API TextLabel : public Control
{
/**
* @brief The start and end property ranges for this control.
+ * @SINCE_1_0.0
*/
enum PropertyRange
{
- PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
- PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices
+ PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1, ///< @SINCE_1_0.0
+ PROPERTY_END_INDEX = PROPERTY_START_INDEX + 1000 ///< Reserve property indices @SINCE_1_0.0
};
/**
* @brief An enumeration of properties belonging to the TextLabel class.
+ * @SINCE_1_0.0
*/
struct Property
{
enum
{
- RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "renderingBackend", The type or rendering e.g. bitmap-based, type INT
- TEXT, ///< name "text", The text to display in UTF-8 format, type STRING
- FONT_FAMILY, ///< name "fontFamily", The requested font family, type STRING
- FONT_STYLE, ///< name "fontStyle", The requested font style, type STRING
- POINT_SIZE, ///< name "pointSize", The size of font in points, type FLOAT
- MULTI_LINE, ///< name "multiLine", The single-line or multi-line layout option, type BOOLEAN
- HORIZONTAL_ALIGNMENT, ///< name "horizontalAlignment", The line horizontal alignment, type STRING, values "BEGIN", "CENTER", "END"
- VERTICAL_ALIGNMENT, ///< name "verticalAlignment", The line vertical alignment, type STRING, values "TOP", "CENTER", "BOTTOM"
- TEXT_COLOR, ///< name "textColor", The text color, type VECTOR4
- SHADOW_OFFSET, ///< name "shadowOffset", The drop shadow offset 0 indicates no shadow, type VECTOR2
- SHADOW_COLOR, ///< name "shadowColor", The color of a drop shadow, type VECTOR4
- UNDERLINE_ENABLED, ///< name "underlineEnabled", The underline enabled flag, type BOOLEAN
- UNDERLINE_COLOR, ///< name "underlineColor", The color of the underline, type VECTOR4
- UNDERLINE_HEIGHT, ///< name "underlineHeight", Overrides the underline height from font metrics, type FLOAT
- ENABLE_MARKUP ///< name "enableMarkup", Whether the mark-up processing is enabled. type BOOLEAN
+ RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "renderingBackend", The type or rendering e.g. bitmap-based, type INT @SINCE_1_0.0
+ TEXT, ///< name "text", The text to display in UTF-8 format, type STRING @SINCE_1_0.0
+ FONT_FAMILY, ///< name "fontFamily", The requested font family, type STRING @SINCE_1_0.0
+ FONT_STYLE, ///< name "fontStyle", The requested font style, type STRING @SINCE_1_0.0
+ POINT_SIZE, ///< name "pointSize", The size of font in points, type FLOAT @SINCE_1_0.0
+ MULTI_LINE, ///< name "multiLine", The single-line or multi-line layout option, type BOOLEAN @SINCE_1_0.0
+ HORIZONTAL_ALIGNMENT, ///< name "horizontalAlignment", The line horizontal alignment, type STRING, values "BEGIN", "CENTER", "END" @SINCE_1_0.0
+ VERTICAL_ALIGNMENT, ///< name "verticalAlignment", The line vertical alignment, type STRING, values "TOP", "CENTER", "BOTTOM" @SINCE_1_0.0
+ TEXT_COLOR, ///< name "textColor", The text color, type VECTOR4 @SINCE_1_0.0
+ SHADOW_OFFSET, ///< name "shadowOffset", The drop shadow offset 0 indicates no shadow, type VECTOR2 @SINCE_1_0.0
+ SHADOW_COLOR, ///< name "shadowColor", The color of a drop shadow, type VECTOR4 @SINCE_1_0.0
+ UNDERLINE_ENABLED, ///< name "underlineEnabled", The underline enabled flag, type BOOLEAN @SINCE_1_0.0
+ UNDERLINE_COLOR, ///< name "underlineColor", The color of the underline, type VECTOR4 @SINCE_1_0.0
+ UNDERLINE_HEIGHT, ///< name "underlineHeight", Overrides the underline height from font metrics, type FLOAT @SINCE_1_0.0
+ ENABLE_MARKUP ///< name "enableMarkup", Whether the mark-up processing is enabled. type BOOLEAN @SINCE_1_0.0
};
};
/**
* @brief Create the TextLabel control.
*
+ * @SINCE_1_0.0
* @return A handle to the TextLabel control.
*/
static TextLabel New();
/**
* @brief Create the TextLabel control.
*
+ * @SINCE_1_0.0
* @param[in] text The text to display.
* @return A handle to the TextLabel control.
*/
/**
* @brief Creates an empty handle.
+ * @SINCE_1_0.0
*/
TextLabel();
/**
* @brief Copy constructor.
*
+ * @SINCE_1_0.0
* @param[in] handle The handle to copy from.
*/
TextLabel( const TextLabel& handle );
/**
* @brief Assignment operator.
*
+ * @SINCE_1_0.0
* @param[in] handle The handle to copy from.
* @return A reference to this.
*/
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~TextLabel();
* If the BaseHandle points is a TextLabel the downcast returns a valid handle.
* If not the returned handle is left empty.
*
+ * @SINCE_1_0.0
* @param[in] handle Handle to an object
* @return handle to a TextLabel or an empty handle
*/
/**
* @brief Creates a handle using the Toolkit::Internal implementation.
*
+ * @SINCE_1_0.0
* @param[in] implementation The Control implementation.
*/
DALI_INTERNAL TextLabel( Internal::TextLabel& implementation );
/**
* @brief Allows the creation of this Control from an Internal::CustomActor pointer.
*
+ * @SINCE_1_0.0
* @param[in] internal A pointer to the internal CustomActor.
*/
explicit DALI_INTERNAL TextLabel( Dali::Internal::CustomActor* internal );
const unsigned int TOOLKIT_MAJOR_VERSION = 1;
const unsigned int TOOLKIT_MINOR_VERSION = 1;
-const unsigned int TOOLKIT_MICRO_VERSION = 16;
+const unsigned int TOOLKIT_MICRO_VERSION = 22;
const char * const TOOLKIT_BUILD_DATE = __DATE__ " " __TIME__;
#ifdef DEBUG_ENABLED
{
PrintVersion()
{
- std::cout << "DALi Toolkit: " << TOOLKIT_MAJOR_VERSION << "." << TOOLKIT_MINOR_VERSION << "." << TOOLKIT_MICRO_VERSION << " (" << TOOLKIT_BUILD_DATE << ")" << std::endl;
+ std::cerr << "DALi Toolkit: " << TOOLKIT_MAJOR_VERSION << "." << TOOLKIT_MINOR_VERSION << "." << TOOLKIT_MICRO_VERSION << " (" << TOOLKIT_BUILD_DATE << ")" << std::endl;
}
};
PrintVersion TOOLKIT_VERSION;
{
/**
* @brief DALi Toolkit namespace.
+ * @SINCE_1_0.0
*/
namespace Toolkit
{
/**
* @brief Control Orientation namespace.
+ * @SINCE_1_0.0
*/
namespace ControlOrientation
{
/**
* @brief The internal orientation of a control.
+ * @SINCE_1_0.0
*/
enum Type
{
- Up, ///< The contents of control are in a vertical layout, from top to bottom
- Left, ///< The contents of control are in a horizontal layout, from left to right
- Down, ///< The contents of control are in a vertical layout, from bottom to top
- Right ///< The contents of control are in a horizontal layout, from right to left
+ Up, ///< The contents of control are in a vertical layout, from top to bottom @SINCE_1_0.0
+ Left, ///< The contents of control are in a horizontal layout, from left to right @SINCE_1_0.0
+ Down, ///< The contents of control are in a vertical layout, from bottom to top @SINCE_1_0.0
+ Right ///< The contents of control are in a horizontal layout, from right to left @SINCE_1_0.0
};
} // namespace ControlOrientation
/**
* @brief Query whether an orientation is horizontal.
*
+ * @SINCE_1_0.0
* @param[in] orientation The orientation.
* @return True if the orientation is horizontal.
*/
class KeyboardFocusManager;
}
/**
- * @addtogroup dali_toolkit_focus_manager
+ * @addtogroup dali_toolkit_managers
* @{
*/
* | keyboardFocusChanged | @ref FocusChangedSignal() |
* | keyboardFocusGroupChanged | @ref FocusGroupChangedSignal() |
* | keyboardFocusedActorAenterKey | @ref FocusedActorEnterKeySignal() |
+ * @SINCE_1_0.0
*/
class DALI_IMPORT_API KeyboardFocusManager : public BaseHandle
{
* @brief Create a KeyboardFocusManager handle; this can be initialised with KeyboardFocusManager::New().
*
* Calling member functions with an uninitialised handle is not allowed.
+ * @SINCE_1_0.0
*/
KeyboardFocusManager();
* @brief Destructor
*
* This is non-virtual since derived Handle types must not contain data or virtual methods.
+ * @SINCE_1_0.0
*/
~KeyboardFocusManager();
/**
* @brief Get the singleton of KeyboardFocusManager object.
*
+ * @SINCE_1_0.0
* @return A handle to the KeyboardFocusManager control.
*/
static KeyboardFocusManager Get();
* Only one actor can be focused at the same time. The actor must
* be in the stage already and keyboard focusable.
*
- * @pre The KeyboardFocusManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be focused
* @return Whether the focus is successful or not
+ * @pre The KeyboardFocusManager has been initialized.
+ * @pre The Actor has been initialized.
*/
bool SetCurrentFocusActor(Actor actor);
/**
* @brief Get the current focused actor.
*
- * @pre The KeyboardFocusManager has been initialized.
+ * @SINCE_1_0.0
* @return A handle to the current focused actor or an empty handle if no actor is focused.
+ * @pre The KeyboardFocusManager has been initialized.
*/
Actor GetCurrentFocusActor();
* chain in the given direction (according to the focus traversal
* order).
*
- * @pre The KeyboardFocusManager has been initialized.
+ * @SINCE_1_0.0
* @param direction The direction of focus movement
* @return true if the movement was successful
+ * @pre The KeyboardFocusManager has been initialized.
*/
bool MoveFocus(Control::KeyboardFocus::Direction direction);
* @brief Clear the focus from the current focused actor if any, so
* that no actor is focused in the focus chain.
*
- * It will emit focus changed signal without current focused actor
+ * It will emit focus changed signal without current focused actor.
+ * @SINCE_1_0.0
* @pre The KeyboardFocusManager has been initialized.
*/
void ClearFocus();
* @brief Set whether the focus movement should be looped within the same focus group.
*
* The focus movement is not looped by default.
- * @pre The KeyboardFocusManager has been initialized.
+ * @SINCE_1_0.0
* @param enabled Whether the focus movement should be looped
+ * @pre The KeyboardFocusManager has been initialized.
*/
void SetFocusGroupLoop(bool enabled);
/**
* @brief Get whether the focus movement should be looped within the same focus group.
*
- * @pre The KeyboardFocusManager has been initialized.
+ * @SINCE_1_0.0
* @return Whether the focus movement should be looped
+ * @pre The KeyboardFocusManager has been initialized.
*/
bool GetFocusGroupLoop() const;
*
* Layout controls set themselves as focus groups by default.
*
- * @pre The KeyboardFocusManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be set as a focus group.
* @param isFocusGroup Whether to set the actor as a focus group or not.
+ * @pre The KeyboardFocusManager has been initialized.
+ * @pre The Actor has been initialized.
*/
void SetAsFocusGroup(Actor actor, bool isFocusGroup);
/**
* @brief Check whether the actor is set as a focus group or not.
*
- * @pre The KeyboardFocusManager has been initialized.
- * @pre The Actor has been initialized.
+ * @SINCE_1_0.0
* @param actor The actor to be checked.
* @return Whether the actor is set as a focus group.
+ * @pre The KeyboardFocusManager has been initialized.
+ * @pre The Actor has been initialized.
*/
bool IsFocusGroup(Actor actor) const;
/**
* @brief Returns the closest ancestor of the given actor that is a focus group.
*
+ * @SINCE_1_0.0
* @param actor The actor to be checked for its focus group
* @return The focus group the given actor belongs to or an empty handle if the given actor
* doesn't belong to any focus group
* KeyboardFocusManager and will be added to the focused actor as a
* highlight.
*
+ * @SINCE_1_0.0
+ * @param indicator The indicator actor to be added
* @pre The KeyboardFocusManager has been initialized.
* @pre The indicator actor has been initialized.
- * @param indicator The indicator actor to be added
*/
void SetFocusIndicatorActor(Actor indicator);
/**
* @brief Get the focus indicator actor.
*
- * @pre The KeyboardFocusManager has been initialized.
+ * @SINCE_1_0.0
* @return A handle to the focus indicator actor
+ * @pre The KeyboardFocusManager has been initialized.
*/
Actor GetFocusIndicatorActor();
* @code
* Actor YourCallbackName(Actor currentFocusedActor, Actor proposedActorToFocus, Control::KeyboardFocus::Direction direction);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
PreFocusChangeSignalType& PreFocusChangeSignal();
* @code
* void YourCallbackName(Actor originalFocusedActor, Actor currentFocusedActor);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
FocusChangedSignalType& FocusChangedSignal();
* @code
* void YourCallbackName(Actor currentFocusedActor, bool forward);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
FocusGroupChangedSignalType& FocusGroupChangedSignal();
* @code
* void YourCallbackName(Actor enterPressedActor);
* @endcode
- * @pre The Object has been initialized.
+ * @SINCE_1_0.0
* @return The signal to connect to.
+ * @pre The Object has been initialized.
*/
FocusedActorEnterKeySignalType& FocusedActorEnterKeySignal();
/**
* @brief Creates a new handle from the implementation.
*
+ * @SINCE_1_0.0
* @param[in] impl A pointer to the object.
*/
explicit DALI_INTERNAL KeyboardFocusManager(Internal::KeyboardFocusManager *impl);
// The type of text renderer required
enum RenderingType
{
- RENDERING_SHARED_ATLAS ///< A bitmap-based solution where renderers can share a texture atlas
+ RENDERING_SHARED_ATLAS ///< A bitmap-based solution where renderers can share a texture atlas @SINCE_1_0.0
};
const unsigned int DEFAULT_RENDERING_BACKEND = RENDERING_SHARED_ATLAS;
"overshootEffectColor":"B018",
"overshootAnimationSpeed":120.0,
"overshootSize":[480.0,42.0]
+ },
+ "texteditor":
+ {
+ "pointSize":18,
+ "primaryCursorColor":[0.0,0.72,0.9,1.0],
+ "secondaryCursorColor":[0.0,0.72,0.9,1.0],
+ "cursorWidth":1,
+ "selectionHighlightColor":[0.75,0.96,1.0,1.0],
+ "grabHandleImage" : "{DALI_STYLE_IMAGE_DIR}cursor_handler_drop_center.png",
+ "selectionHandleImageLeft" : {"filename":"{DALI_STYLE_IMAGE_DIR}selection_handle_drop_left.png" },
+ "selectionHandleImageRight": {"filename":"{DALI_STYLE_IMAGE_DIR}selection_handle_drop_right.png" }
+ },
+ "popup":
+ {
+ "popupBackgroundImage":"{DALI_IMAGE_DIR}00_popup_bg.9.png"
+ },
+ "confirmationpopup":
+ {
+ "popupBackgroundImage":"{DALI_IMAGE_DIR}00_popup_bg.9.png"
}
}
}
"overshootEffectColor":"B018",
"overshootAnimationSpeed":360.0,
"overshootSize":[720.0,130.0]
+ },
+ "texteditor":
+ {
+ "pointSize":18,
+ "primaryCursorColor":[0.0,0.72,0.9,1.0],
+ "secondaryCursorColor":[0.0,0.72,0.9,1.0],
+ "cursorWidth":3,
+ "selectionHighlightColor":[0.75,0.96,1.0,1.0],
+ "grabHandleImage" : "{DALI_STYLE_IMAGE_DIR}cursor_handler_drop_center.png",
+ "selectionHandleImageLeft" : {"filename":"{DALI_STYLE_IMAGE_DIR}selection_handle_drop_left.png" },
+ "selectionHandleImageRight": {"filename":"{DALI_STYLE_IMAGE_DIR}selection_handle_drop_right.png" }
}
}
}
+ [Popup](@ref popup)
+ [Scroll View](@ref scroll-view)
+ TableView
+ + [Text Editor](@ref text-editor)
+ [Text Field](@ref text-field)
+ [Text Label](@ref text-label)
--- /dev/null
+<!--
+/**-->
+
+# Copy and Paste (Selection) {#copy-n-paste}
+
+Text can be selected by a long press or double tapping it. Depending on certain conditions a popup could be shown giving options including [CUT][COPY][PASTE], [SELECT ALL] or [CLIPBOARD]. Below these conditions will be explained.
+
+[CUT] or [COPY] send the selected text to the clipboard ready to be pasted directly or via the clipboard UI. Pressing [PASTE] will paste the top item from the clipboard (what has just been copied, possibly from another application). If the system supports a clipboard UI this can be displayed by pressing the [CLIPBOARD] button.
+
+Empty text means the user has not inputted any text, a text-control containing special characters or purely whitespace is not empty.
+
+Below shows how the popup will look depending on the state of the text-control.
+
+| | |
+|--|--|
+| Condition: Long press/double tap when empty text but clipboard has content | Condition: Long press/double tap when text-control contains text |
+|[PASTE][CLIPBOARD] buttons shown| [CUT][COPY], [SELECT ALL] unless all text selected and [PASTE][CLIPBOARD] if content to paste. |
+| ![ ](../assets/img/text-controls/EmptyTextClipboardHasContent.png) ![ ](./EmptyTextClipboardHasContent.png) | ![ ](../assets/img/text-controls/SelectingText.png) ![ ](./SelectingText.png) |
+| Condition: Long press/double tap popup when text-control contains just whitespace | Condition: Empty text & clipboard empty |
+| Whitespace treated as regular text, [CUT][COPY] shown and [PASTE][CLIPBOARD] if content to paste. As all text is selected there is no need for [SELECT ALL] | No popup shown after longpress/double tap|
+| ![ ](../assets/img/text-controls/SelectAllWhitespace.png) ![ ](./SelectAllWhitespace.png) | ![ ](../assets/img/text-controls/EmptyTextAndNoContentToPaste.png) ![ ](./EmptyTextAndNoContentToPaste.png)|
+| Condition: Longpress/(double tap) on whitespace which is following text | Condition: Tapping text or panning grab handle |
+| [PASTE][CLIPBOARD] shown if something to paste. [SELECT ALL] as more text to select | If content in clipboard [PASTE][CLIPBOARD] popup will be shown. |
+| ![ ](../assets/img/text-controls/SelectWhitespaceAfterText.png) ![ ](./SelectWhitespaceAfterText.png) | ![ ](../assets/img/text-controls/TapAfterCopyingText.png) ![ ](./TapAfterCopyingText.png) |
+
+
+*/
--- /dev/null
+<!--
+/**-->
+
+# Input Style {#input-style}
+
+The input style can be changed through the control properties. All subsequent characters added will be rendered with the new input style.
+
+Note the input style may change if the cursor is updated by tapping in a new position.
+
+Current supported input style properties are:
+
+- *INPUT_COLOR* Sets the input color. The property expects a Vector4 with the red, green, blue and alpha values clamped between 0 and 1.
+- *INPUT_FONT_FAMILY* Sets the input font's family name. The property expects the name of the font. If the new text is not supported by the given font a suitable one will be set.
+- *INPUT_FONT_STYLE* Sets the input font's style. The property expects a json formatted string with the font's style. See the [Font Selection](@ref font-selection) section for more details.
+- *INPUT_POINT_SIZE* Sets the input font's size. The property expects a float with the font's size in points. See the [Font Selection](@ref font-selection) section for more details.
+
+*/
field.text = "<color value='#FF0000'>Red Text</color>"; // Color packed with the web color format (6 characters).
~~~
+## \<font\>
+
+Sets the font values of the characters inside the tag.
+
+Supported attributes are:
+- *family* The name of the font.
+- *size* The size of the font in points.
+- *weight* The weight of the font.
+- *width* The width of the font
+- *slant* The slant of the font.
+
+See the [Font Selection](@ref font-selection) to have a view of the possible values for the *weight*, *width* and *slant* attributes.
+
+~~~{.cpp}
+// C++
+field.SetProperty( TextLabel::Property::TEXT, "<font family='SamsungSans' weight='bold'>Hello world</font>" );
+~~~
+
+~~~{.js}
+// JavaScript
+
+field.text = "<font family='SamsungSans' weight='bold'>Hello world</font>";
+~~~
+
*/
[TOC]
# Resource Image Scaling {#resourceimagescaling}
-
-## Introduction
-
-While common uses of images in DALi applications involve fixed sized images
-under the developer's control, e.g. for button backgrounds, in other cases such as galleries and wallpapers an application must display a variety of images and adapt to different screen sizes and densities.
-For these situations, DALi provides a facility to scale a `ResourceImage` while it is being loaded.
-
-Look at the following example.
+
+## Introduction {#resourceimagescaling-introduction}
+
+Resource Image Scaling provides automatic image resizing (without changing aspect) based on settings provided by the developer.
+This operation is performed at load time.
+
+### Developer options:
+* A target size of the image - this could be the full screen size for example.
+* A Fitting mMde - This determines how the image is fitted to the target dimensions. If necessary the image will be cropped, or have borders added automatically.
+* A Sampling Mode - This determines the quality of the scaling (by specifying the type of filtering to use).
+
+### Benefits of Resource Image Scaling:
+* Scaled image will typically be 1-to-1 size ratio with on screen pixels, giving quality benefits.
+* Scaling performed at load time, so run time speed is improved.
+* Ease of use allows applications handling lots of images of different sizes to be created quickly and easily.
+
+## Use-Case Example {#resourceimagescaling-basicexample}
+While common uses of images in DALi applications involve fixed sized images under the developer's control, e.g. for button backgrounds, in other cases such as galleries and wallpapers an application must display a variety of images and adapt to different screen sizes and densities.
+
+There are more code examples later in this document under [API usage](#resourceimagescaling-apidetails). For now we will just give one full code example to show how this feature is used..
+
Let's say we are writing a home-screen application for a smartphone.
Here we have a large, square image that we want to set as the wallpaper on a tall and narrow phone screen.
We want to fill the screen without distorting the image or having black borders, and wasting as few pixels from the source image as possible.
-
+
![ ](../assets/img/image-scaling/example-scale-to-fill-problem.jpg)
![ ](example-scale-to-fill-problem.jpg)
-
-DALi provides the concept of a `FittingMode` to specify how a source image is mapped into a target rectangle, and the one we need here is `FittingMode::SCALE_TO_FILL` as it will cover all of the pixels of the target.
+
+DALi provides the concept of a `FittingMode` to specify how a source image is mapped into a target rectangle, and the one we need here is `FittingMode::SCALE_TO_FILL` as it guarrentees to cover all of the pixels of the target dimensions specified.
A second concept of a `SamplingMode` controls how source image pixels are combined during the scaling and allows the developer to trade speed for quality.
-Since our image is to be loaded once and reused, we should use `SamplingMode::BOX_THEN_LINEAR` which is the highest quality option.
-We can pass the stage dimensions to the `ResourceImage` creator function as the desired rectangle and ask it to map the image to the screen as follows:
-
+Since our image is to be loaded once and reused, we use `SamplingMode::BOX_THEN_LINEAR` which is the highest quality option.
+
+In this case, `SCALE_TO_FILL` will perform this sequence of operations:
+
+![ ](../assets/img/image-scaling/example-scale-to-fill-sequence.jpg) ![ ](example-scale-to-fill-sequence.jpg)
+
+We can pass the stage dimensions to the `ResourceImage` creator function as the desired rectangle and ask it to map the image to the screen as shown here:
+
~~~{.cpp}
-// C++
-ResourceImage image = ResourceImage::New(
+ // C++
+ ResourceImage image = ResourceImage::New(
"gallery-large-12.jpg",
Dali::ImageDimensions( stage.GetSize().x, stage.GetSize().y ),
Dali::FittingMode::SCALE_TO_FILL,
samplingMode: "BOX_THEN_LINEAR"
});
~~~
-
-In this case, `SCALE_TO_FILL` will perform this sequence of operations:
-
-| SCALE_TO_FILL Example |
-| ------------ |
-| ![ ](../assets/img/image-scaling/example-scale-to-fill-sequence.jpg) ![ ](example-scale-to-fill-sequence.jpg) |
-| <sub> **1.** *The source image.* **2.** *The source scaled-down to match the screen size.* **3.** *The borders of the image are trimmed to match the shape of the screen.* **4.** *The image fits exactly on the phone screen with no scaling required while rendering.* </sub> |
-
-
-## API Details {#resourceimagescalingapidetails}
-
-The new function of `ResourceImage` has the following scaling-related parameters:
-* **path**: Identifier for the image (allows raw image width and height to be retrieved).
-* **requested dimensions**: These are either `(0,0)`, a width, a height, or a (width, height) pair and either directly, or after reading the image raw dimensions and doing some math, define a target rectangle to fit the image to.
-* **fitting mode**: one of four strategies for mapping images onto the target rectangle.
-* **sampling mode** Different quality options for the scaling.
-
-### Target dimensions for fitting {#resourceimagescalingtargetdimensions}
-
+
+
+## Workflow {#resourceimagescaling-workflow}
+
+![ ](../assets/img/image-scaling/workflow-main.png) ![ ](workflow-main.png)
+
+The workflow for achieving the final scaled image is (in order):
+
+- Target Size: Determine target size (from source image size and any user specified target dimensions).
+- Target Image Dimensions: Determine the size the image should be scaled to (taking Fitting Mode into account)
+- Scaling: Perform a scale to target image dimensions using the specified Sampling mode.
+- Crop or Add Borders: Automatically perfomed as necessary to maintain final target aspect (actual stored data size could be smaller).
+
+
+
+### Determine Target Dimensions {#resourceimagescaling-targetdimensions}
+
+![ ](../assets/img/image-scaling/workflow-1.png) ![ ](workflow-1.png)
+
An application has several options for specifying the target rectangle for the image to be fitted to.
The application may request dimensions through `ResourceImage::New()`:
+
+ - `Not specifying either dimension`: IE. Width and Height set to 0 - The target dimensions become the same as the source.
- 1. `(0, 0)`, which is equivalent to not specifying any dimensions
- 2. `(x != 0, 0)` or `(0, y != 0)`, i.e. just one dimension specified
- 3. `(x != 0, y != 0)`, i.e. both dimensions specified
+ - `Just one dimension specified, Width OR Height (the other dimension set to 0)`:
+ The unspecified dimension will be derived from the specified one whilst maintaining the aspect of the source image. The specified and calculated dimensions become the target dimensions. See more on this case [below](#resourceimagescalingzerodimensions).
+
+ - `Width AND Height both specified` The requested dimensions pass straight through to become the target for fitting.
+
+![ ](../assets/img/image-scaling/scaling-fitting-target-dimensions.png) ![ ](scaling-fitting-target-dimensions.png)
-In **case 1.** no scaling will be attempted.
-The image will be loaded at its raw dimensions.
-In **case 2.** the unspecified dimension will be derived from the specified one and the aspect ratio of the raw dimensions.
-This specified dimension and calculated dimension pair pass on as the target dimension for fitting.
-See more on this case [below](#resourceimagescalingzerodimensions).
-In **case 3.** the requested dimensions pass straight through to become the target for fitting.
+The result of this process is an `(x, y)` target size to fit the image in the next step.
+
-The result of this process is an `(x, y)` tuple defining a box to fit the image to in the next step.
-#### Examples {#resourceimagescalingtargetdimensionsexamples}
-If we have a `(320, 240)` image called "flower.jpg", we use these three options in code as below.
+### Target Image Dimensions {#resourceimagescaling-targetimagedimensions}
-**Case 1**:
+![ ](../assets/img/image-scaling/workflow-2.png) ![ ](workflow-2.png)
+
+#### Fitting Mode
+
+DALi provides a number of strategies for mapping the pixels of an image onto the target box derived above.
+It provides a `FittingMode` enumeration to the developer to select a mapping or fitting approach.
+These are `SCALE_TO_FILL`, `SHRINK_TO_FIT`, `FIT_WIDTH`, and `FIT_HEIGHT` and their effect is best appreciated visually:
+
+The operation of each of these modes is as follows:
+
+| `FittingMode` | **Operation** |
+| ------------- | ------------- |
+| `SCALE_TO_FILL` | Centers the image on the target box and uniformly scales it so that it matches the target in one dimension and extends outside the target in the other. Chooses the dimension to match that results in the fewest pixels outside the target. Trims away the parts of the image outside the target box so as to match it exactly. This guarentees all of the target area is filled. |
+| `SHRINK_TO_FIT` | Centers the image on the target box and uniformly scales it so that it matches the target in one dimension and fits inside it in the other. This guarentees that all of the source image area is visible. |
+| `FIT_WIDTH` | Centers the image on the target box and uniformly scales it so that it matches the target width without regard for the target height. |
+| `FIT_HEIGHT` | Centers the image on the target box and uniformly scales it so that it matches the target in height without regard for the target width. |
+
+
+![ ](../assets/img/image-scaling/fitting-mode-options.png) ![ ](fitting-mode-options.png)
+
+<sub> **Fitting modes**: *The top row shows the effect of each mode when a tall target rectangle is applied to a square image. The middle row applies a wide target to a square raw image. The bottom row uses a target with the same aspect ratio as the raw image. This example shows that `SCALE_TO_FILL` is the only option for which the dimensions of the fitted image result fill all the area of the target. Others would be letterboxed with borders. `SHRINK_TO_FIT` is always equal to one of `FIT_WIDTH` or `FIT_HEIGHT`: in each case it is the minimum of them. As a special case, where the aspect ratio of raw image and target match, all fitting modes generate an exact match final image and are equivalent to each other.* </sub>
+
+
+Note: The image is scaled to the same aspect and shrunk to fit depending on fitting mode. It is not upscaled. See: [Upscaling](#resourceimagescalingupscaling).
+
+
+
+### Scaling {#resourceimagescaling-scaling}
+
+![ ](../assets/img/image-scaling/workflow-3.png) ![ ](workflow-3.png)
+
+To perform the scaling stage, the source image is scaled to a (factor of) the target image size using the specified Sampling Mode/
+
+The process of scaling an image can be expensive in CPU cycles and add latency to the loading of each resource.
+To allow the developer to trade-off speed against quality for different use cases, DALi provides the `SamplingMode` enum, which can be passed to `ResourceImage::New()`.
+Two of these modes produce bitmaps which differ from the dimensions calculated by the fitting algorithm and so have a memory trade-off as well. The full set of modes is explained below.
+
+| `SamplingMode` | **Operation** |
+| ------------- | --------- |
+| `NEAREST` | Use simple point sampling when scaling. For each pixel in output image, just one pixel is chosen from the input image. This is the fastest, crudest option but suffers the worst from aliasing artifacts so should only be used for fast previews, or where the source image is known to have very low-frequency features. |
+| `LINEAR` | Uses a weighted bilinear filter with a `(2,2)` footprint when scaling. For each output pixel, four input pixels are averaged from the input image. This is a good quality option, equivalent to the GPU's filtering and works well at least down to a `0.5` scaling. |
+| `BOX` | Uses an iterated `(2,2)` box filter to repeatedly halve the image in both dimensions, averaging adjacent pixels until the the result is approximately right for the fitting target rectangle. For each output pixel some number of pixels from the sequence `[4,16,64,256,1024,...]` are averaged from the input image, where the number averaged depends on the degree of scaling requested. This provides a very high quality result and is free from aliasing artifacts because of the iterated averaging. *The resulting bitmap will not exactly match the dimensions calculated by the fitting mode but it will be within a factor of two of it and have the same aspect ratio as it.* |
+| `BOX_THEN_NEAREST` | Applies the `BOX` mode to get within a factor of two of the fitted dimensions, and then finishes off with `NEAREST` to reach the exact dimensions. |
+| `BOX_THEN_LINEAR` | Applies the `BOX` mode to get within a factor of two of the fitted dimensions, and then finishes off with `LINEAR` to reach the exact dimensions. This is the slowest option and of equivalent quality to `BOX`. It is superior to `BOX` in that is uses an average of 62% of the memory and exactly matches the dimensions calculated by fitting. **This is the best mode for most use cases**. |
+| `NO_FILTER` | Disables scaling altogether. In conjunction with `SCALE_TO_FILL` mode this can be useful as the edge trimming of that fitting mode is still applied. An example would be a gallery application, where a database of prescaled thumbnails of approximately the correct size need to be displayed in a regular grid of equal-sized cells, while being loaded at maximum speed. |
+
+
+Here are all the modes applied to scaling-down a `(640,720)` line art and text JPEG image to a `(218, 227)` thumbnail:
+
+| | | |
+| ---- | ---- | --- |
+| ![ ](../assets/img/image-scaling/sampling_modes_no_filter.png) ![ ](sampling_modes_no_filter.png) | ![ ](../assets/img/image-scaling/sampling_modes_nearest.png) ![ ](sampling_modes_nearest.png) | ![ ](../assets/img/image-scaling/sampling_modes_linear.png) ![ ](sampling_modes_linear.png) |
+| **NO_FILTER** | **NEAREST** | **LINEAR** |
+| ![ ](../assets/img/image-scaling/sampling_modes_box.png) ![ ](sampling_modes_box.png) | ![ ](../assets/img/image-scaling/sampling_modes_box_then_nearest.png) ![ ](sampling_modes_box_then_nearest.png) | ![ ](../assets/img/image-scaling/sampling_modes_box_then_linear.png) ![ ](sampling_modes_box_then_linear.png) |
+| **BOX** | **BOX_THEN_NEAREST** | **BOX_THEN_LINEAR** |
+
+These are screenshots, showing how the images are rendered in a DALi demo.
+There is an additional level of GPU bilinear filtering happening at render time.
+The best way to get a feel for the best sampling mode for different image types is to play with the [examples](#resourceimagescaling-samplingmodesdemoexamples).
+
+
+
+### Crop or Add Borders {#resourceimagescaling-croporaddborders}
+
+![ ](../assets/img/image-scaling/workflow-4.png) ![ ](workflow-4.png)
+
+Lastly, the image data will be cropped, or have borders added automatically as necessary.
+This is done to ensure the image correctly fits the aspect of the target window, whilst maintaining the aspect of the source image.
+
+Images that have an alpha channel will be given transparent borders. Otherwise black is used.
+
+
+
+## Using the API (With source code examples) {#resourceimagescaling-apidetails}
+
+This section contains more detail about using the API to setup the desired behaviour.
+
+`ResourceImage` :: New has the following parameters:
+- **path**: Identifier for the image (allows raw image width and height to be retrieved).
+- **requested dimensions**: These are either `(0,0)`, a width, a height, or a (width, height) pair and either directly, or after reading the image raw dimensions and doing some math, define a target rectangle to fit the image to.
+- **fitting mode**: one of four strategies for mapping images onto the target rectangle.
+- **sampling mode** Different quality options for the scaling.
+
+### Code Examples {#resourceimagescaling-targetdimensionsexamples}
+If we have a `(320, 240)` image called "flower.jpg", we use these options in code as below.
+
+**Case 1**: In these two equivalent loads, the target dimensions are not specified, so will be `(320, 240)` so the image will be loaded at its raw dimensions without modification.
~~~{.cpp}
// C++
ResourceImage image1 = ResourceImage::New( "flower.png" );
var image1 = new dali.ResourceImage( { url:"flower.png" } );
var image2 = new dali.ResourceImage( { url:"flower.png", width:0, height:0 } );
~~~
-In these two equivalent loads, the target dimensions will be `(320, 240)` so the image will be loaded at its raw dimensions without modification.
+
-**Case 2**:
+**Case 2**: In these loads, the target dimensions will be `(160, 120)` as the zero dimension is derived from the aspect ratio of the raw image.
~~~{.cpp}
// C++
ResourceImage image1 = ResourceImage::New( "flower.png", ImageDimensions( 160, 0 ) );
var image1 = new dali.ResourceImage( { url:"flower.png", width:160, height:0 } );
var image2 = new dali.ResourceImage( { url:"flower.png", width:0, height:120 } );
~~~
-In these loads, the target dimensions will be `(160, 120)` as the zero dimension is derived from the aspect ratio of the raw image.
+
-**Case 3**:
+**Case 3**: In this load, the target dimensions will be `(111, 233)`.
~~~{.cpp}
// C++
ResourceImage image = ResourceImage::New( "flower.png", ImageDimensions( 111, 233 ) );
// JavaScript
var image = new dali.ResourceImage( { url:"flower.png", width:111, height:233 } );
~~~
-In this load, the target dimensions will be `(111, 233)`.
-
-### Image Pixel Dimensions {#resourceimagescalingsamplingmodesdimensionflow}
-
-DALi derives the pixel width and height of loaded resource images from a sequence of calculations with four inputs:
-
- 1. The dimensions requested via `ResourceImage` new function, either of which may be passed as zeros
- 2. The dimensions of the raw image before loading
- 3. The fitting mode requested
- 4. The sampling mode requested
-
-The dimensions requested do not correspond 1:1 with the exact pixel width and height of the image once loaded: they are just one of the four inputs to the process which determines those dimensions.
-
-| Flow of image dimensions from API to loaded image |
-| ------------ |
-| ![ ](../assets/img/image-scaling/concept-rectangles.jpg) ![ ](concept-rectangles.jpg) |
-| <sub> *Image dimensions requested through the API are either absent (**a.**), a height (**b.**), a width (**c.**) or a full (width, height) pair (**d.**). In case **d.** this is the target for fitting (**i.**). In cases **a.**, **b.**, and **c.**, the raw image dimensions (**e.**) are also needed to define the target (examples: **f.**, **g.**, **h.**). This target, the **FittingMode**, and the raw size (**e.**), are used to derive the fitted size (**j.**). This is the size that a perfect scaling would achieve. This fitted size, the **Sampling Mode**, and the raw size (**e.**) are used to derive the final pixel width and height (**k.** **l.** **m.**, depending on **Sampling Mode**).* </sub> |
-
-The diagram above shows the key `(x,y)` image dimensions used by DALi in its load-time scaling pipeline visualized as rectangles.
-They are:
-
- 1. **Requested**: The dimensions passed by the app.
- 2. **Raw**: The dimensions stored in the resource.
- 3. **Target**: The box to fit the image into derived from 1. and 2.
- 4. **Fitted**: The ideal scaled-down size of the image.
- 5. **Scaled Pixels** The final pixel width and height resulting from the (possibly approximate) scaling.
-
-This should help to understand how the parameters given to DALi influence the final image loaded. The (x, y) passed define a *target* to the fit the image to rather than a new size for the image directly.
-The fitting mode defines a strategy for fitting the raw image to the target.
-The sampling mode has two options which cause the fitted dimensions to be exceeded, while the others cause it to be matched exactly.
-
-The pipeline from the values passed from the application to the *natural size* of the image is different. If no dimension is passed, the raw image size is read from the image resource. If only one dimension is passed, the explicitly set dimension will be used for the **natural size** and the unspecified dimension will match the actual loaded pixel dimension. When both are specified that becomes the 'natural size' even if it differs from the actual pixel dimensions loaded. This [requires some care in rendering to avoid distortion](#resourceimagescalingsamplingmodesrendernaturalsize).
-
-### Fitting an image's dimensions to the target box {#resourceimagescalingfittingmodes}
-
-DALi provides a number of strategies for mapping the pixels of an image onto the target box derived above.
-It provides a `FittingMode` enumeration to the developer to select a mapping or fitting approach.
-These are `SCALE_TO_FILL`, `SHRINK_TO_FIT`, `FIT_WIDTH`, and `FIT_HEIGHT` and their effect is best appreciated visually:
-
-| FittingMode Options |
-| ------------------- |
-| ![ ](../assets/img/image-scaling/fitting-mode-options.jpg) ![ ](fitting-mode-options.jpg) |
-| <sub> **Fitting modes**: *The top row shows the effect of each mode when a tall target rectangle is applied to a square image. The middle row applies a wide target to a square raw image. The bottom row uses a target with the same aspect ratio as the raw image. These examples show that `SCALE_TO_FILL` is the only option for which the dimensions of the fitted image result exactly match the target. The others are larger or smaller, with a different aspect ratio. `SHRINK_TO_FIT` is always equal to one of `FIT_WIDTH` or `FIT_HEIGHT`: in each case it is the minimum of them. As a special case, where the aspect ratio of raw image and target match, all fitting modes generate an exact match final image and are equivalent to each other.* </sub> |
-
-The operation of each of these modes is as follows:
-
-| `FittingMode` | **Operation** |
-| ------------- | --------- |
-| `SCALE_TO_FILL` | Centers the image on the target box and uniformly scales it so that it matches the target in one dimension and extends outside the target in the other. Chooses the dimension to match that results in the fewest pixels outside the target. Trims away the parts of the image outside the target box so as to match it exactly. |
-| `SHRINK_TO_FIT` | Centers the image on the target box and uniformly scales it so that it matches the target in one dimension and fits inside it in the other. |
-| `FIT_WIDTH` | Centers the image on the target box and uniformly scales it so that it matches the target width without regard for the target height. |
-| `FIT_HEIGHT` | Centers the image on the target box and uniformly scales it so that it matches the target in height and ignores the target width. |
-
-These modes differ only when the target box has a different aspect ratio to the raw image. Using this, if the application knows a priori what the image dimensions are, it can scale down the image by requesting dimensions that have the same aspect ratio as the raw dimensions:
+
+
+### Fitting an image's dimensions to the target box {#resourceimagescaling-codeexamplesfittingmodes}
+
+The result of the fitting modes defined [here](#resourceimagescaling-targetimagedimensions) only differ when the target box has a different aspect ratio than the source image.
+Images may still be scaled down, depending on the target dimensions, but the specified fitting mode will not have an effect.
+
+EG:
~~~{.cpp}
// C++
// Image on 'disk' is 320x240.
var image = new dali.ResourceImage( { url:"flower.png", width:32, height:24});
// Image will be loaded at (32, 24), regardless of fitting mode.
~~~
+
+### Passing a Zero Dimension {#resourceimagescalingzerodimensions}
+
+Passing in a single zero dimension is equivalent to specifying `FIT_WIDTH` or `FIT_HEIGHT` `FittingMode`s. When a non-zero width and zero height are specified, the fitting done will be identical to the result using `FittingMode` `FIT_WIDTH`. When passing a zero width and non-zero height, the effect of applying the chosen `FittingMode` to the calculated target dimensions is always identical to applying the `FIT_HEIGHT` mode.
+
+* `ResourceImage::New( ImageDimensions( x, 0 ), <ANY_FITTING_MODE> )` =
+ `ResourceImage::New( ImageDimensions( x, <ANYTHING> ), FittingMode::FIT_WIDTH )`
+* `ResourceImage::New( ImageDimensions( 0, y ), <ANY_FITTING_MODE> )` =
+ `ResourceImage::New( ImageDimensions( <ANYTHING>, y), FittingMode::FIT_HEIGHT )`
+
+This falls out of the the fact that the fitting modes are strategies for the case when the aspect ratio of the raw image differs from the aspect ratio of the target dimensions, but the zero dimension behavior always ensures that the target dimensions have the same aspect ratio as the raw image's so the fitting modes are all equivalent.
+
+Therefore, if `(x!=0, y=0)`, fittingMode = `FIT_WIDTH`,
+and if `(x=0, y=!0)`, fittingMode = `FIT_HEIGHT`, irrespective of fitting mode passed by the application (if any).
+This shortcut is provided as a convenience to the developer and allows FIT_WIDTH or FIT_HEIGHT to be specified compactly:
+~~~{.cpp}
+// C++
+// FIT_WIDTH:
+ResourceImage image = ResourceImage::New("flower.png", ImageDimensions(x, 0));
+// FIT_HEIGHT:
+ResourceImage image = ResourceImage::New("flower.png", ImageDimensions(0, y));
+~~~
+~~~{.js}
+// JavaScript
+// FIT_WIDTH:
+var image = new dali.ResourceImage( {
+ url: "flower.png",
+ width: x,
+ height: 0
+});
+// FIT_HEIGHT:
+var image = new dali.ResourceImage( {
+ url: "flower.png",
+ width: 0,
+ height: y
+});
+~~~
+
+Note:
+- If both values are specified as 0, both dimensions are taken from the source image.
+- If both dimensions are not 0, this value becomes the 'natural size' even if it differs from the actual pixel dimensions loaded. [This requires some care in rendering to avoid distortion](#resourceimagescaling-samplingmodesrendernaturalsize).
+
-### Quality Versus Speed and Memory Options {#resourceimagescalingsamplingmodes}
-
-The process of scaling an image can be expensive in CPU cycles and add latency to the loading of each resource.
-To allow the developer to trade-off speed against quality for different use cases, DALi provides the `SamplingMode` enum, which can be passed to `ResourceImage::New()`.
-Two of these modes produce bitmaps which differ from the dimensions calculated by the fitting algorithm and so have a memory trade-off as well. The full set of modes is explained below.
-
-| `SamplingMode` | **Operation** |
-| ------------- | --------- |
-| `NEAREST` | Use simple point sampling when scaling. For each pixel in output image, just one pixel is chosen from the input image. This is the fastest, crudest option but suffers the worst from aliasing artifacts so should only be used for fast previews, or where the source image is known to have very low-frequency features. |
-| `LINEAR` | Uses a weighted bilinear filter with a `(2,2)` footprint when scaling. For each output pixel, four input pixels are averaged from the input image. This is a good quality option, equivalent to the GPU's filtering and works well at least down to a `0.5` scaling. |
-| `BOX` | Uses an iterated `(2,2)` box filter to repeatedly halve the image in both dimensions, averaging adjacent pixels until the the result is approximately right for the fitting target rectangle. For each output pixel some number of pixels from the sequence `[4,16,64,256,1024,...]` are averaged from the input image, where the number averaged depends on the degree of scaling requested. This provides a very high quality result and is free from aliasing artifacts because of the iterated averaging. *The resulting bitmap will not exactly match the dimensions calculated by the fitting mode but it will be within a factor of two of it and have the same aspect ratio as it.* |
-| `BOX_THEN_NEAREST` | Applies the `BOX` mode to get within a factor of two of the fitted dimensions, and then finishes off with `NEAREST` to reach the exact dimensions. |
-| `BOX_THEN_LINEAR` | Applies the `BOX` mode to get within a factor of two of the fitted dimensions, and then finishes off with `LINEAR` to reach the exact dimensions. This is the slowest option and of equivalent quality to `BOX`. It is superior to `BOX` in that is uses an average of 62% of the memory and exactly matches the dimensions calculated by fitting. **This is the best mode for most use cases**. |
-| `NO_FILTER` | Disables scaling altogether. In conjunction with `SCALE_TO_FILL` mode this can be useful as the edge trimming of that fitting mode is still applied. An example would be a gallery application, where a database of prescaled thumbnails of approximately the correct size need to be displayed in a regular grid of equal-sized cells, while being loaded at maximum speed. |
-
-Here are all the modes applied to scaling-down a `(640,720)` line art and text JPEG image to a `(218, 227)` thumbnail:
-
-| | | |
-| ---- | ---- | --- |
-| ![ ](../assets/img/image-scaling/sampling_modes_no_filter.png) ![ ](sampling_modes_no_filter.png) | ![ ](../assets/img/image-scaling/sampling_modes_nearest.png) ![ ](sampling_modes_nearest.png) | ![ ](../assets/img/image-scaling/sampling_modes_linear.png) ![ ](sampling_modes_linear.png) |
-| **NO_FILTER** | **NEAREST** | **LINEAR** |
-| ![ ](../assets/img/image-scaling/sampling_modes_box.png) ![ ](sampling_modes_box.png) | ![ ](../assets/img/image-scaling/sampling_modes_box_then_nearest.png) ![ ](sampling_modes_box_then_nearest.png) | ![ ](../assets/img/image-scaling/sampling_modes_box_then_linear.png) ![ ](sampling_modes_box_then_linear.png) |
-| **BOX** | **BOX_THEN_NEAREST** | **BOX_THEN_LINEAR** |
-
-These are screenshots, showing how the images are rendered in a DALi demo.
-There is an additional level of GPU bilinear filtering happening at render time.
-The best way to get a feel for the best sampling mode for different image types is to play with the [examples](#resourceimagescalingsamplingmodesexamples).
+### Code Examples for Sampling Modes {#resourceimagescaling-codeexamplessamplingmodes}
+
-In the following code example the same image is loaded to be a thumbnail but with differing quality, speed, and memory implications.
+In the following code example an image is loaded to be a thumbnail but with differing quality, speed, and memory implications.
~~~{.cpp}
// C++
ResourceImage image1 = ResourceImage::New( "flower.png",
ImageDimensions( 240, 240 ), FittingMode::SCALE_TO_FILL, SamplingMode::NEAREST );
-
+
ResourceImage image2 = ResourceImage::New( "flower.png",
ImageDimensions( 240, 240 ), FittingMode::SCALE_TO_FILL, SamplingMode::NO_FILTER );
-
+
ResourceImage image3 = ResourceImage::New( "flower.png",
ImageDimensions( 240, 240 ), FittingMode::SCALE_TO_FILL, SamplingMode::BOX );
-
+
ResourceImage image4 = ResourceImage::New( "flower.png",
ImageDimensions( 240, 240 ), FittingMode::SCALE_TO_FILL, SamplingMode::BOX_THEN_LINEAR );
~~~
fittingMode:"SCALE_TO_FILL", samplingMode:"BOX_THEN_LINEAR"
} );
~~~
+
+
+
-If we imagine flower.jpg is a 560*512 photo with high frequency details, the results of this are:
+### Notes on speed VS quality {#resourceimagescaling-speedvsquality}
+
+If we imagine flower.jpg is a 560*512 photo with high frequency details, the results of this are (image references are from above example):
* `image1` loads fast, uses minimal space, has poor quality.
* `image2` loads even faster, uses 4.6 * minimal space, has good quality.
* `image3` loads moderately slow, uses 1.3 * minimal space, has good quality.
* `image4` loads slowest, uses minimal space, has good quality.
-
+
Note that `BOX`, `BOX_THEN_NEAREST` and `BOX_THEN_LINEAR` can work particularly well for JPEG images as they can use fast downscaling typically built-in to the JPEG codec on supported platforms on the fly while decoding. In this case the caveats about using them having a speed trade-off given above do not apply.
+
+
-## Passing a Zero Dimension {#resourceimagescalingzerodimensions}
-Passing in a single zero dimension is effectively a shortcut for specifying `FIT_WIDTH` or `FIT_HEIGHT` `FittingMode`s. When a non-zero width and zero height are specified, the fitting done will be identical to the result using `FittingMode` `FIT_WIDTH`. When passing a zero width and non-zero height, the effect of applying the chosen `FittingMode` to the calculated target dimensions is always identical to applying the `FIT_HEIGHT` mode.
-
-* `ResourceImage::New( ImageDimensions( x, 0 ), <ANY_FITTING_MODE> )` =
- `ResourceImage::New( ImageDimensions( x, <ANYTHING> ), FittingMode::FIT_WIDTH )`
-* `ResourceImage::New( ImageDimensions( 0, y ), <ANY_FITTING_MODE> )` =
- `ResourceImage::New( ImageDimensions( <ANYTHING>, y), FittingMode::FIT_HEIGHT )`
-
-This falls out of the the fact that the fitting modes modes are strategies for the case when the aspect ratio of the raw image differs from the aspect ratio of the target dimensions, but the zero dimension behavior always ensures that the target dimensions have the same aspect ratio as the raw image's so the fitting modes are all equivalent.
-Therefore, if `(x!=0, y=0)`, fittingMode = `FIT_WIDTH`,
-and if `(x=0, y=!0)`, fittingMode = `FIT_HEIGHT`, irrespective of fitting mode passed by the application (if any).
-This shortcut is provided as a convenience to the developer and allows FIT_WIDTH or FIT_HEIGHT to be specified compactly:
-~~~{.cpp}
-// C++
-// FIT_WIDTH:
-ResourceImage image = ResourceImage::New("flower.png", ImageDimensions(x, 0));
-// FIT_HEIGHT:
-ResourceImage image = ResourceImage::New("flower.png", ImageDimensions(0, y));
-~~~
-~~~{.js}
-// JavaScript
-// FIT_WIDTH:
-var image = new dali.ResourceImage( {
- url: "flower.png",
- width: x,
- height: 0
-});
-// FIT_HEIGHT:
-var image = new dali.ResourceImage( {
- url: "flower.png",
- width: 0,
- height: y
-});
-~~~
-
-## Upscaling
+## Demo Examples {#resourceimagescaling-samplingmodesdemoexamples}
+
+Load time image scaling is spread throughout the DALi examples.
+Search for `"ImageDimensions"` in the dali-demo project to see it used.
+There is also a specific demo to show all of the fitting and scaling modes.
+which lives in the demo project at `examples/image-scaling-and-filtering`.
+
+![ ](../assets/img/image-scaling/demo-fitting-sampling.png) ![ ](./demo-fitting-sampling.png)
+
+Touch the arrows in the top corners to changes image.
+Drag the resize handle in the corner of the image to change the requested size and trigger an immediate image reload.
+Use the buttons at the bottom of the screen to select any of the fitting and sampling modes from the popups which appear.
+This demo does not take any of the special measures [described here](#resourceimagescaling-naturalsizecompensation) to correct for the natural size != pixel dimensions discrepancy so all fitting modes other than `SCALE_TO_FILL` show distortion.
+
+A second specific demo shows the effect of a filter mode on a single image loaded into various requested rectangles side by side.
+It can be found under `examples/image-scaling-irregular-grid`.
+
+![ ](../assets/img/image-scaling/demo-sampling-modes.jpg) ![ ](./demo-sampling-modes.jpg)
+
+Touch the button at top-left to change image.
+The button at top-right changes sampling mode.
+You will see strong differences between sampling modes where the image contains high frequency details such as hair and in the large black and white image, but much less in some others such as the Statue of Liberty which is mostly covered by a smooth gradient.
+
+
+## Further Notes {#resourceimagescaling-furthernotes}
+
+### Upscaling {#resourceimagescaling-upscaling}
+
DALi refuses to upscale images at load time in order to conserve memory.
-If the application requests a size for an image that is larger than its raw dimensions, DALi will instead return an image with the same aspect ratio but limited to the largest dimensions that do not exceed the raw ones.
+If the application requests an image size the specified fitting mode) would require scaling up, DALi will instead return an image with the same aspect ratio but limited to the largest dimensions that do not exceed the raw ones.
+EG. The actual image could be a fraction of the size of the target image dimensions.
Upscaling can still be effected at render time by setting the size of an actor to the desired size.
+
+
-## Compressed Textures and Scaling
-
+### Compressed Textures and Scaling {#resourceimagescaling-compressedtextures}
+
Compressed textures cannot be scaled at load time as their formats are designed to be uploaded directly to GPU memory. To achieve scaling of compressed textures, set the desired size on the attached `ImageActor` for scaling at render time instead.
+
+
-## Compensation for Natural Size != Pixel Width / Height {#resourceimagescalingsamplingmodesrendernaturalsize}
-
+### Compensation for Natural Size != Pixel Width / Height {#resourceimagescaling-naturalsizecompensation}
+
Because the *natural size* of an image is
-[taken from the requested dimensions](#resourceimagescalingsamplingmodesdimensionflow)
+[taken from the requested dimensions](#resourceimagescaling-samplingmodesdimensionflow)
passed to `ResourceImage::New()` rather than passing through the same calculations that result in the eventual pixel width and height loaded,
the *natural size* and pixel dimensions of an image will differ when loaded with scaling.
It is inherent in the definition of fitting modes other than `SCALE_TO_FILL` not to match the requested dimensions, so in general, images loaded with them must have this mismatch between *natural size* and actual pixel width.
-
-It is not possible in general to draw a scaled resource image using its natural size as the `ImageActor`'s size without it appearing stretched in one dimension.
+
+It is not possible in general to draw a scaled resource image using its natural size as the `ImageView`'s size without it appearing stretched in one dimension.
This is the case for example by default with size negotiation in effect or when an image is simply passed to an actor at creation time.
-
+
There are circumstance, however, in which the the natural size of a resource image loaded will exactly match its post-load pixel dimensions:
-
-1. No scaling is requested.
-1. The application chooses a combination of requested dimensions, fitting mode, and sampling mode which the scaling sub-system can match exactly. This is the case:
+
+- No scaling is requested.
+- The application chooses a combination of requested dimensions, fitting mode, and sampling mode which the scaling sub-system can match exactly. This is the case:
* For all downscaling using `SCALE_TO_FILL` fitting mode and not using `BOX` or `NO_FILTER` sampling modes.
* The app uses `SHRINK_TO_FIT`, `FIT_WIDTH`, or `FIT_HEIGHT` and the requested dimensions passed-in are both smaller than the raw ones and have the same aspect ratio as them, and it is not using `BOX` or `NO_FILTER` sampling modes.
-
+
In these cases the image may be used freely in layouts controlled by size negotiation.
Additionally, if the requested size has the same aspect ratio as the eventual pixel array loaded, and the fitting mode is `SCALE_TO_FILL` or `BOX` and `NO_FILTER` sampling modes are avoided, even if they don't match in dimensions exactly, the eventual image will be drawn without aspect ratio distortion although it will be scaled at render time.
-
-The fitting and scaling modes [demo](#resourceimagescalingsamplingmodesexamples) allows this behavior to be be explored dynamically when the fitting mode is changed from `SCALE_TO_FILL`.
-
+
+The fitting and scaling modes [demo](#resourceimagescalingsamplingmodesdemoexamples) allows this behavior to be be explored dynamically when the fitting mode is changed from `SCALE_TO_FILL`.
+
The application can of course only pass dimensions which are just right if it happens to know the raw dimensions or if it accesses the the image resource and reads the raw dimensions from its header.
-
+
The application can get a scaled resource image rendered correctly to screen with one of three strategies:
-
+
1. Use one of the special cases above.
2. Read the image header from disk, recreate the dimension deriving, fitting, and sampling logic described in this document, and use that to generate a pair of requested dimensions which match the eventual image dimensions.
3. Use the requested dimensions it really wants to but then read the image header from disk, recreate the dimension deriving, fitting, and sampling logic described in this document, and set the size of an `ImageActor` to that size explicitly rather than relying on the *natural size* of the image.
+
-## Examples {#resourceimagescalingsamplingmodesexamples}
-Load time image scaling is spread throughout the DALi examples.
-Search for `"ImageDimensions"` in the dali-demo project to see it used.
-There is also a specific demo to show all of the fitting and scaling modes.
-which lives in the demo project at `examples/image-scaling-and-filtering`.
-
-![ ](../assets/img/image-scaling/demo-fitting-sampling.jpg) ![ ](./demo-fitting-sampling.jpg)
-
-Touch the arrows in the top corners to changes image.
-Drag the green button in the corner of the image to change the requested size and trigger an immediate image reload.
-Use the buttons at the bottom of the screen to select any of the fitting and sampling modes from the popups which appear.
-This demo does not take any of the special measures [described above](#resourceimagescalingsamplingmodesrendernaturalsize) to correct for the natural size != pixel dimensions discrepancy so all fitting modes other than `SCALE_TO_FILL` show distortion.
-
-A second specific demo shows the effect of a filter mode on a single image loaded into various requested rectangles side by side.
-It can be found under `examples/image-scaling-irregular-grid`.
-
-![ ](../assets/img/image-scaling/demo-sampling-modes.jpg) ![ ](./demo-sampling-modes.jpg)
-
-Touch the button at top-left to change image.
-The button at top-right changes sampling mode.
-You will see strong differences between sampling modes where the image contains high frequency details such as hair and in the large black and white image, but much less in some others such as the Statue of Liberty which is mostly covered by a smooth gradient.
@class _Guide_Resource_Image_Scaling
*/
--- /dev/null
+<!--
+/**-->
+
+# Text Editor {#text-editor}
+
+## Overview
+
+The Dali::Toolkit::TextEditor is a control which provides a multi-line editable text.
+
+### Basic usage
+
+Add the text-editor to the stage.
+
+~~~{.cpp}
+// C++
+
+TextEditor editor = TextEditor::New();
+
+Stage::GetCurrent().Add( editor );
+~~~
+
+~~~{.js}
+// JavaScript
+
+var editor = new dali.TextEditor();
+
+dali.stage.add( editor );
+~~~
+
+When the TextEditor is tapped, it will automatically gain the keyboard focus. Key events will then result in text being inserted.
+After text has been entered, it can be retrieved from the TEXT property.
+
+~~~{.cpp}
+// C++
+
+Property::Value editorText = editor.GetProperty( TextEditor::Property::TEXT );
+std::cout << "Received text: " << editorText.Get< std::string >() << std::endl;
+~~~
+
+~~~{.js}
+// JavaScript
+
+console.log( editor.text );
+~~~
+
+### Font Selection
+
+By default TextEditor will automatically select a suitable font from the platform. However, a different font could be selected. See the [Font Selection](@ref font-selection) section for more details.
+
+### Mark-up Style
+
+Mark-up tags can be used to change the style of the text. See the [Mark-up Style](@ref markup-style) section for more details.
+
+### Input Style
+
+The input style can be changed through the control properties.See the [Input Style](@ref input-style) section for more details.
+
+### Text Alignment
+
+TextEditor displays a multi-line of text, which will scroll if there is not enough room for the text displayed.
+If there is enough room, then the text can be aligned horizontally to the beginning, end, or center of the available area:
+
+~~~{.cpp}
+// C++
+
+editor.SetProperty( TextEditor::Property::HORIZONTAL_ALIGNMENT, "BEGIN" ); // "CENTER" or "END"
+~~~
+
+~~~{.js}
+// JavaScript
+
+editor.HorizontalAlignment = "BEGIN"; // "CENTER" or "END"
+~~~
+
+### Copy and Paste (Selection)
+
+Text can be selected by a long press or double tapping it. See the [Copy and Paste](@ref copy-n-paste) section for more details.
+
+### TextEditor Decorations
+
+#### Color
+
+To change the color of the text, the recommended way is to use the TEXT_COLOR property.
+
+~~~{.cpp}
+// C++
+editor.SetProperty( TextEditor::Property::TEXT_COLOR, Color::CYAN );
+~~~
+
+~~~{.js}
+// JavaScript
+
+editor.textColor = dali.COLOR_CYAN;
+~~~
+
+### TextEditor Properties
+
+ Name (JavaScript) | Name (C++) | Type | Writable | Animatable
+-----------------------------------|--------------------------------------|--------------|--------------|-----------
+ renderingBackend | RENDERING_BACKEND | INTEGER | O | X
+ text | TEXT | STRING | O | X
+ textColor | TEXT_COLOR | VECTOR4 | O | X
+ fontFamily | FONT_FAMILY | STRING | O | X
+ fontStyle | FONT_STYLE | STRING | O | X
+ pointSize | POINT_SIZE | FLOAT | O | X
+ horizontalAlignment | HORIZONTAL_ALIGNMENT | STRING | O | X
+ verticalAlignment | VERTICAL_ALIGNMENT | STRING | O | X
+ scrollThreshold | SCROLL_THRESHOLD | FLOAT | O | X
+ scrollSpeed | SCROLL_SPEED | FLOAT | O | X
+ primaryCursorColor | PRIMARY_CURSOR_COLOR | VECTOR4 | O | X
+ secondaryCursorColor | SECONDARY_CURSOR_COLOR | VECTOR4 | O | X
+ enableCursorBlink | ENABLE_CURSOR_BLINK | BOOLEAN | O | X
+ cursorBlinkInterval | CURSOR_BLINK_INTERVAL | FLOAT | O | X
+ cursorBlinkDuration | CURSOR_BLINK_DURATION | FLOAT | O | X
+ cursorWidth | CURSOR_WIDTH | INTEGER | O | X
+ grabHandleImage | GRAB_HANDLE_IMAGE | STRING | O | X
+ grabHandlePressedImage | GRAB_HANDLE_PRESSED_IMAGE | STRING | O | X
+ selectionHandleImageLeft | SELECTION_HANDLE_IMAGE_LEFT | STRING | O | X
+ selectionHandleImageRight | SELECTION_HANDLE_IMAGE_RIGHT | STRING | O | X
+ selectionHandlePressedImageLeft | SELECTION_HANDLE_PRESSED_IMAGE_LEFT | STRING | O | X
+ selectionHandlePressedImageRight | SELECTION_HANDLE_PRESSED_IMAGE_RIGHT | STRING | O | X
+ selectionHandleMarkerImageLeft | SELECTION_HANDLE_MARKER_IMAGE_LEFT | MAP | O | X
+ selectionHandleMarkerImageRight | SELECTION_HANDLE_MARKER_IMAGE_RIGHT | MAP | O | X
+ selectionHighlightColor | SELECTION_HIGHLIGHT_COLOR | VECTOR4 | O | X
+ decorationBoundingBox | DECORATION_BOUNDING_BOX | RECTANGLE | O | X
+ enableMarkup | ENABLE_MARKUP | BOOLEAN | O | X
+ inputColor | INPUT_COLOR | VECTOR4 | O | X
+ inputFontFamily | INPUT_FONT_FAMILY | STRING | O | X
+ inputFontStyle | INPUT_FONT_STYLE | STRING | O | X
+ inputPointSize | INPUT_POINT_SIZE | FLOAT | O | X
+
+@class TextEditor
+
+*/
Before any text has been entered, the TextField can display some placeholder text.
An alternative placeholder can be displayed when the TextField has keyboard focus.
-For example a TextField used to enter a username could initially show "Unknown Name", and then show "Enter Name." when the cursor is shown.
+For example a TextField used to enter a username could initially show "Unknown Name", and then show "Enter Name." when the cursor is shown.
+
+Note *CR+LF* new line characters are replaced by a *LF* one.
~~~{.cpp}
// C++
### Input Style
-The input style can be changed through the control properties. Current supported input style properties are:
-
-#### INPUT_COLOR
-
-Sets the input color. All subsequent characters added will be rendered with the input color.
-
-Note the input color may change if the cursor is updated by tapping in a new position.
+The input style can be changed through the control properties. See the [Input Style](@ref input-style) section for more details.
### Text Alignment
### Copy and Paste (Selection)
-Text can be selected by a long press or double tapping it. Depending on certain conditions a popup could be shown giving options including [CUT][COPY][PASTE], [SELECT ALL] or [CLIPBOARD]. Below these conditions will be explained.
-
-[CUT] or [COPY] send the selected text to the clipboard ready to be pasted directly or via the clipboard UI. Pressing [PASTE] will paste the top item from the clipboard (what has just been copied, possibly from another application). If the system supports a clipboard UI this can be displayed by pressing the [CLIPBOARD] button.
-
-Empty text means the user has not inputted any text, a TextField containing special characters or purely whitespace is not empty.
-
-Below shows how the popup will look depending on the state of the TextField
-
-| | |
-|--|--|
-| Condition: Long press/double tap when empty text but clipboard has content | Condition: Long press/double tap when TextField contains text |
-|[PASTE][CLIPBOARD] buttons shown| [CUT][COPY], [SELECT ALL] unless all text selected and [PASTE][CLIPBOARD] if content to paste. |
-| ![ ](../assets/img/text-controls/EmptyTextClipboardHasContent.png) ![ ](./EmptyTextClipboardHasContent.png) | ![ ](../assets/img/text-controls/SelectingText.png) ![ ](./SelectingText.png) |
-| Condition: Long press/double tap popup when TextField contains just whitespace | Condition: Empty text & clipboard empty |
-| Whitespace treated as regular text, [CUT][COPY] shown and [PASTE][CLIPBOARD] if content to paste. As all text is selected there is no need for [SELECT ALL] | No popup shown after longpress/double tap|
-| ![ ](../assets/img/text-controls/SelectAllWhitespace.png) ![ ](./SelectAllWhitespace.png) | ![ ](../assets/img/text-controls/EmptyTextAndNoContentToPaste.png) ![ ](./EmptyTextAndNoContentToPaste.png)|
-| Condition: Longpress/(double tap) on whitespace which is following text | Condition: Tapping text or panning grab handle |
-| [PASTE][CLIPBOARD] shown if something to paste. [SELECT ALL] as more text to select | If content in clipboard [PASTE][CLIPBOARD] popup will be shown. |
-| ![ ](../assets/img/text-controls/SelectWhitespaceAfterText.png) ![ ](./SelectWhitespaceAfterText.png) | ![ ](../assets/img/text-controls/TapAfterCopyingText.png) ![ ](./TapAfterCopyingText.png) |
+Text can be selected by a long press or double tapping it. See the [Copy and Paste](@ref copy-n-paste) section for more details.
### TextField Decorations
inputMethodSettings | INPUT_METHOD_SETTINGS | MAP | O | X
inputColor | INPUT_COLOR | VECTOR4 | O | X
enableMarkup | ENABLE_MARKUP | BOOLEAN | O | X
+ inputFontFamily | INPUT_FONT_FAMILY | STRING | O | X
+ inputFontStyle | INPUT_FONT_STYLE | STRING | O | X
+ inputPointSize | INPUT_POINT_SIZE | FLOAT | O | X
@class TextField
To display a TextLabel the TEXT property must be set using a UTF-8 string.
+Note *CR+LF* new line characters are replaced by a *LF* one.
+
~~~{.cpp}
// C++
'<(DALI_JS_DIR)/actors/layer-api.cpp',
'<(DALI_JS_DIR)/actors/camera-actor-api.cpp',
'<(DALI_JS_DIR)/constants/constants-wrapper.cpp',
+ '<(DALI_JS_DIR)/controls/control-wrapper.cpp',
+ '<(DALI_JS_DIR)/controls/item-factory-wrapper.cpp',
+ '<(DALI_JS_DIR)/controls/item-view-api.cpp',
+ '<(DALI_JS_DIR)/controls/scroll-view-api.cpp',
'<(DALI_JS_DIR)/animation/animation-api.cpp',
'<(DALI_JS_DIR)/animation/animation-wrapper.cpp',
'<(DALI_JS_DIR)/animation/constrainer-api.cpp',
'cflags': [
'-fPIC',
'-frtti',
- '<!@(pkg-config --cflags dali dali-toolkit)'
+ '<!@(pkg-config --cflags dali-core dali-adaptor-uv dali-toolkit)'
],
'cflags_cc': [
'-frtti' # needed for typeinfo with dali-any
],
'ldflags': [
- '<!@(pkg-config --libs-only-L --libs-only-other dali dali-toolkit)'
+ '<!@(pkg-config --libs-only-L --libs-only-other dali-core dali-adaptor-uv dali-toolkit)'
],
'libraries': [
- '<!@(pkg-config --libs-only-l dali dali-toolkit)'
+ '<!@(pkg-config --libs-only-l dali-core dali-adaptor-uv dali-toolkit)'
]
}]
}
${PLUGING_SRC_DIR}/actors/actor-api.cpp
${PLUGING_SRC_DIR}/actors/layer-api.cpp
${PLUGING_SRC_DIR}/actors/camera-actor-api.cpp
+ ${PLUGING_SRC_DIR}/controls/control-wrapper.cpp
+ ${PLUGING_SRC_DIR}/controls/item-factory-wrapper.cpp
+ ${PLUGING_SRC_DIR}/controls/item-view-api.cpp
+ ${PLUGING_SRC_DIR}/controls/scroll-view-api.cpp
${PLUGING_SRC_DIR}/constants/constants-wrapper.cpp
${PLUGING_SRC_DIR}/animation/animation-api.cpp
${PLUGING_SRC_DIR}/animation/animation-wrapper.cpp
set_target_properties(dali_addon PROPERTIES EXCLUDE_FROM_ALL "FALSE")
-SET(PKG_LIST dali
+SET(PKG_LIST dali-core
+ dali-adaptor-uv
dali-toolkit)
INCLUDE(FindPkgConfig)
--- /dev/null
+ var window= {
+ x:0,
+ y:0,
+ width:1920,
+ height: 1080,
+ transparent: false,
+ name:'itemview-example'
+ };
+
+ var viewMode={
+ 'stereoscopic-mode':'mono', // stereo-horizontal, stereo-vertical, stereo-interlaced,
+ 'stereoBase': 65 // Distance in millimeters between left/right cameras typically between (50-70mm)
+ };
+
+ var options= {
+ 'window': window,
+ 'viewMode': viewMode,
+ }
+
+//desktop
+//var dali = require('../build/Release/dali')( options );
+
+//target
+var dali = require('dali')( options );
+
+var items = [];
+var button;
+var stageSize;
+
+var itemView;
+var itemFactory;
+
+var currentLayoutIndex = 0;
+var totalItemCount = 100;
+
+var imageDir = "./images/";
+
+var daliApp = {};
+
+daliApp.createItemView = function() {
+
+ // Create item view data
+ var itemViewData = [];
+ for (var itemId = 0; itemId < totalItemCount; itemId++)
+ {
+ var data = {};
+ data["template"] = "template-item-list"; // Create items initially with list template
+ data["icon_path"] = imageDir + "icon-" + itemId % 3 + ".png";
+ data["title_text"] = "Item " + itemId;
+ itemViewData[itemId] = data;
+ }
+
+ // Create item factory and set the data
+ itemFactory = new dali.ItemFactory();
+ itemFactory.jsonTemplateFile = "./scripts/item-template.json";
+ itemFactory.data = itemViewData;
+
+ // Create item view
+ stageSize = dali.stage.getSize();
+ itemView = new dali.Control("ItemView", itemFactory);
+ itemView.size = [stageSize.x, stageSize.y, 0.0];
+ itemView.parentOrigin = dali.CENTER_LEFT;
+ itemView.anchorPoint = dali.CENTER_LEFT;
+ itemView.refreshInterval = 4.0;
+
+ // Add item view to the stage
+ dali.stage.add( itemView );
+
+ // Create scroll bar for item view
+ var scrollBar = new dali.Control("ScrollBar");
+ scrollBar.parentOrigin = dali.TOP_RIGHT;
+ scrollBar.anchorPoint = dali.TOP_RIGHT;
+ scrollBar.widthResizePolicy = "FIT_TO_CHILDREN";
+ scrollBar.heightResizePolicy = "FILL_TO_PARENT";
+ itemView.add(scrollBar);
+
+ // Add the list and grid layouts
+ itemView.addLayout(dali.ITEM_LAYOUT_LIST); // layout index 0
+ itemView.addLayout(dali.ITEM_LAYOUT_GRID); // layout index 1
+
+ // Set custom item size for list layout
+ itemView.setItemSize(0, [stageSize.x, stageSize.y * 0.1, 0.0]);
+
+ // Set custom item size for grid layout
+ var layoutMargin = 120;
+ itemView.setItemSize(1, [(stageSize.x - layoutMargin) / 4, stageSize.y * 0.2, 0.0]);
+
+ // Activate the list layout
+ itemView.activateLayout(0, itemView.size);
+
+ // Create button for layout switching
+ button = new dali.Control("PushButton");
+ button.size = [100.0, 60.0, 0.0];
+ button.position = [-20.0, 20.0, 0.0];
+ button.parentOrigin = dali.TOP_RIGHT;
+ button.anchorPoint = dali.TOP_RIGHT;
+ button.labelText = "Switch";
+ dali.stage.add( button );
+
+ // Connect a signal callback to button pressed signal
+ button.on("pressed", daliApp.buttonPressedEvent);
+}
+
+daliApp.buttonPressedEvent = function( button ) {
+
+ // Calculate the layout index for the next layout to switch to
+ currentLayoutIndex++;
+ currentLayoutIndex = currentLayoutIndex % itemView.getLayoutCount();
+
+ // Activate the next layout
+ itemView.activateLayout(currentLayoutIndex, [stageSize.x, stageSize.y, 0.0], 0.0);
+
+ // Change the item template in item view data as we want to change the layout of the items
+ var data = itemFactory.data;
+ for (var itemId = 0; itemId < totalItemCount; itemId++)
+ {
+ if(currentLayoutIndex == 0)
+ {
+ // List layout
+ data[itemId]["template"] = "template-item-list"; // Create items with list template
+ }
+ else
+ {
+ // Grid layout
+ data[itemId]["template"] = "template-item-grid"; // Create items with grid template
+ }
+ }
+ itemFactory.data = data;
+}
+
+function startup()
+{
+ daliApp.init();
+}
+
+daliApp.init = function()
+{
+ daliApp.createItemView();
+}
+
+startup();
+
}
// desktop
-//var dali = require('./build/Release/dali')( options );
+//var dali = require('../build/Release/dali')( options );
// target
var dali = require('dali')( options );
'view-mode': viewMode,
}
-
// desktop
-//var dali = require('./build/Release/dali')( options );
+//var dali = require('../build/Release/dali')( options );
// target
var dali = require('dali')( options );
'view-mode': viewMode,
}
-var imageDir = "./";
+var imageDir = "./images/";
// desktop
-//var dali = require('./build/Release/dali')( options );
+//var dali = require('../build/Release/dali')( options );
// target
var dali = require('dali')( options );
--- /dev/null
+{
+ "templates":
+ {
+ "template-item-list":
+ {
+ "name":"item",
+ "type":"Actor",
+ "position":[0,0,0],
+ "anchorPoint":"TOP_LEFT",
+ "parentOrigin":"TOP_LEFT",
+ "actors":
+ [
+ {
+ "name":"icon",
+ "type":"ImageView",
+ "image":
+ {
+ "rendererType" : "imageRenderer",
+ "imageUrl": "{icon_path}"
+ },
+ "position":[20.0, 0.0, 0.0],
+ "size":[70.0, 70.0, 0.0],
+ "color":[1.0,1.0,1.0,1.0],
+ "anchorPoint":"CENTER_LEFT",
+ "parentOrigin":"CENTER_LEFT",
+ "actors":
+ [
+ {
+ "name":"title",
+ "anchorPoint":"CENTER_LEFT",
+ "parentOrigin":"CENTER_RIGHT",
+ "type":"TextLabel",
+ "position": [30.0, 0.0, 0.0],
+ "size":[200.0, 70.0, 0.0],
+ "pointSize":30,
+ "fontFamily":"HelveticaNeue",
+ "fontStyle":"Bold",
+ "horizontalAlignment":"BEGIN",
+ "verticalAlignment":"CENTER",
+ "textColor": [1.0,0.0,1.0,1.0],
+ "text":"{title_text}"
+ }
+ ]
+ }
+ ]
+ },
+
+ "template-item-grid":
+ {
+ "name":"item",
+ "type":"Actor",
+ "position":[0,0,0],
+ "anchorPoint":"TOP_LEFT",
+ "parentOrigin":"TOP_LEFT",
+ "actors":
+ [
+ {
+ "name":"icon",
+ "type":"ImageView",
+ "image":
+ {
+ "rendererType" : "imageRenderer",
+ "imageUrl": "{icon_path}"
+ },
+ "position":[0.0, -10.0, 0.0],
+ "size":[70.0, 70.0, 0.0],
+ "color":[1.0,1.0,1.0,1.0],
+ "anchorPoint":"CENTER",
+ "parentOrigin":"CENTER",
+ "actors":
+ [
+ {
+ "name":"title",
+ "anchorPoint":"TOP_CENTER",
+ "parentOrigin":"BOTTOM_CENTER",
+ "type":"TextLabel",
+ "position": [0.0,10.0,0.0],
+ "size":[100.0, 100.0, 0.0],
+ "pointSize":22,
+ "fontFamily":"HelveticaNeue",
+ "fontStyle":"Bold",
+ "horizontalAlignment":"CENTER",
+ "textColor": [1.0,0.0,1.0,1.0],
+ "text":"{title_text}"
+ }
+ ]
+ }
+ ]
+ }
+ }
+}
+
--- /dev/null
+ var window= {
+ x:0,
+ y:0,
+ width:1920,
+ height:1080,
+ transparent: false,
+ name:'scrollview-example'
+ };
+
+ var viewMode={
+ 'stereoscopic-mode':'mono', // stereo-horizontal, stereo-vertical, stereo-interlaced,
+ 'stereoBase': 65 // Distance in millimeters between left/right cameras typically between (50-70mm)
+ };
+
+ var options= {
+ 'window': window,
+ 'viewMode': viewMode,
+ }
+
+//desktop
+//var dali = require('../build/Release/dali')( options );
+
+//target
+var dali = require('dali')( options );
+
+var stageSize;
+var scrollView;
+var scrollBar;
+
+var imageDir = "./images/";
+
+var daliApp = {};
+
+daliApp.createScrollView = function() {
+
+ // Create a scroll view
+ scrollView = new dali.Control("ScrollView");
+ stageSize = dali.stage.getSize();
+ scrollView.size = [stageSize.x, stageSize.y, 0.0];
+ scrollView.parentOrigin = dali.CENTER;
+ scrollView.anchorPoint = dali.CENTER;
+
+ dali.stage.add( scrollView );
+
+ // Add actors to a scroll view with 4 pages
+ var pageRows = 1;
+ var pageColumns = 3;
+ for(var pageRow = 0; pageRow < pageRows; pageRow++)
+ {
+ for(var pageColumn = 0; pageColumn < pageColumns; pageColumn++)
+ {
+ var pageActor = new dali.Control();
+ pageActor.widthResizePolicy = "FILL_TO_PARENT";
+ pageActor.heightResizePolicy = "FILL_TO_PARENT";
+ pageActor.parentOrigin = dali.CENTER;
+ pageActor.anchorPoint = dali.CENTER;
+ pageActor.position = [pageColumn * stageSize.x, pageRow * stageSize.y, 0.0];
+ pageActor.name = "pageActor" + pageColumn;
+
+ // Add images in a 5x4 grid layout for each page
+ var imageRows = 4;
+ var imageColumns = 5;
+ var margin = 10.0;
+ var imageSize = [(stageSize.x / imageColumns) - margin, (stageSize.y / imageRows) - margin, 0.0];
+
+ for(var row = 0; row < imageRows; row++)
+ {
+ for(var column = 0; column < imageColumns;column++)
+ {
+ var imageView = new dali.Control("ImageView");
+ var imageId = (row * imageColumns + column) % 2 + 1;
+ imageView.image = imageDir + "image-" + imageId + ".jpg";
+ imageView.parentOrigin = dali.CENTER;
+ imageView.anchorPoint = dali.CENTER;
+ imageView.size = imageSize;
+ imageView.position = [ margin * 0.5 + (imageSize[0] + margin) * column - stageSize.x * 0.5 + imageSize[0] * 0.5,
+ margin * 0.5 + (imageSize[1] + margin) * row - stageSize.y * 0.5 + imageSize[1] * 0.5,
+ 0.0 ];
+ pageActor.add(imageView);
+ var position = imageView.position;
+ }
+ }
+
+ scrollView.add( pageActor );
+ }
+ }
+
+ // Set scroll view to have 3 pages in X axis and allow page snapping,
+ // and also disable scrolling in Y axis.
+ var scrollMode = {
+ xAxisScrollEnabled : true,
+ xAxisSnapToInterval : stageSize.x, // Define the snap points
+ xAxisScrollBoundary : stageSize.x * pageColumns, // i.e. Define 3 pages
+ yAxisScrollEnabled : false
+ }
+
+ scrollView.setScrollMode(scrollMode);
+
+ // Create a horizontal scroll bar in the bottom of scroll view (optional)
+ scrollBar = new dali.Control("ScrollBar");
+ scrollBar.parentOrigin = dali.BOTTOM_LEFT;
+ scrollBar.anchorPoint = dali.TOP_LEFT;
+ scrollBar.widthResizePolicy = "FIT_TO_CHILDREN";
+ scrollBar.heightResizePolicy = "FILL_TO_PARENT";
+ scrollBar.orientation = [0, 0, 270];
+ scrollBar.scrollDirection = "Horizontal";
+ scrollView.add(scrollBar);
+
+ // Connect to the onRelayout signal
+ scrollView.on("onRelayout", daliApp.onScrollViewRelayout);
+}
+
+daliApp.onScrollViewRelayout = function( button ) {
+
+ // Set the correct scroll bar size after size negotiation of scroll view is done
+ scrollBar.size = [0.0, scrollView.getRelayoutSize(dali.DIMENSION_WIDTH), 0.0 ];
+}
+
+function startup()
+{
+ daliApp.init();
+}
+
+daliApp.init = function()
+{
+ daliApp.createScrollView();
+}
+
+startup();
+
'view-mode': viewMode,
}
-var imageDir = "./";
+var imageDir = "./images/";
// desktop
-//var dali = require('./build/Release/dali')( options );
+//var dali = require('../build/Release/dali')( options );
// target
var dali = require('dali')( options );
--- /dev/null
+{
+ "templates":
+ {
+ "template-item-list":
+ {
+ "name":"item",
+ "type":"Actor",
+ "position":[0,0,0],
+ "anchorPoint":"TOP_LEFT",
+ "parentOrigin":"TOP_LEFT",
+ "actors":
+ [
+ {
+ "name":"icon",
+ "type":"ImageView",
+ "image":
+ {
+ "rendererType" : "imageRenderer",
+ "imageUrl": "{icon_path}"
+ },
+ "position":[20.0, 0.0, 0.0],
+ "size":[70.0, 70.0, 0.0],
+ "color":[1.0,1.0,1.0,1.0],
+ "anchorPoint":"CENTER_LEFT",
+ "parentOrigin":"CENTER_LEFT",
+ "actors":
+ [
+ {
+ "name":"title",
+ "anchorPoint":"CENTER_LEFT",
+ "parentOrigin":"CENTER_RIGHT",
+ "type":"TextLabel",
+ "position": [30.0, 0.0, 0.0],
+ "size":[200.0, 70.0, 0.0],
+ "pointSize":30,
+ "fontFamily":"HelveticaNeue",
+ "fontStyle":"Bold",
+ "horizontalAlignment":"BEGIN",
+ "verticalAlignment":"CENTER",
+ "textColor": [1.0,0.0,1.0,1.0],
+ "text":"{title_text}"
+ }
+ ]
+ }
+ ]
+ },
+
+ "template-item-grid":
+ {
+ "name":"item",
+ "type":"Actor",
+ "position":[0,0,0],
+ "anchorPoint":"TOP_LEFT",
+ "parentOrigin":"TOP_LEFT",
+ "actors":
+ [
+ {
+ "name":"icon",
+ "type":"ImageView",
+ "image":
+ {
+ "rendererType" : "imageRenderer",
+ "imageUrl": "{icon_path}"
+ },
+ "position":[0.0, -10.0, 0.0],
+ "size":[70.0, 70.0, 0.0],
+ "color":[1.0,1.0,1.0,1.0],
+ "anchorPoint":"CENTER",
+ "parentOrigin":"CENTER",
+ "actors":
+ [
+ {
+ "name":"title",
+ "anchorPoint":"TOP_CENTER",
+ "parentOrigin":"BOTTOM_CENTER",
+ "type":"TextLabel",
+ "position": [0.0,10.0,0.0],
+ "size":[100.0, 100.0, 0.0],
+ "pointSize":22,
+ "fontFamily":"HelveticaNeue",
+ "fontStyle":"Bold",
+ "horizontalAlignment":"CENTER",
+ "textColor": [1.0,0.0,1.0,1.0],
+ "text":"{title_text}"
+ }
+ ]
+ }
+ ]
+ }
+ }
+}
+
URL: https://review.tizen.org/gerrit/#/q/project:platform/core/uifw/dali-toolkit
Distribution: Tizen
Source0: %{name}-%{version}.tar.gz
-Requires: dali
-# Do NOT put an adaptor here - it is an application choice which adaptor to use
BuildRequires: pkgconfig
BuildRequires: pkgconfig(dlog)
BuildRequires: cmake
-BuildRequires: pkgconfig(dali)
BuildRequires: pkgconfig(dali-core)
BuildRequires: pkgconfig(dali-toolkit)
BuildRequires: nodejs-devel
+# DALi JS applications using dali-addon always run on dali-adaptor-uv.
+BuildRequires: pkgconfig(dali-adaptor-uv)
+
%description
DALi Node.JS addon
cd "%{addonBuildDir}"
%make_install
-cp %{addonDir}/line-mesh.js %{installDir}/line-mesh.js
+cp -R %{addonDir}/examples %{installDir}/examples
%clean
Name: dali-toolkit
Summary: The OpenGLES Canvas Core Library Toolkit
-Version: 1.1.16
+Version: 1.1.22
Release: 1
Group: System/Libraries
License: Apache-2.0 and BSD-2-Clause and MIT
Requires(post): /sbin/ldconfig
Requires(postun): /sbin/ldconfig
-Requires: dali
-# Do NOT put an adaptor here - it is an application choice which adaptor to use
+
BuildRequires: pkgconfig
BuildRequires: pkgconfig(dlog)
-BuildRequires: pkgconfig(dali)
BuildRequires: pkgconfig(dali-core)
+# dali-toolkit only need to know the interfaces(APIs) of dali-adaptor(the devel package).
+# It doesn't need to know which adaptor will be used by applications.
+# Applications or dali-addon will decide which one they will use.
+BuildRequires: dali-adaptor-devel
+
#############################
# profile setup
#############################
var anim = new dali.Animation( 4 );
var rotation = new dali.Rotation( 90, 0, 0 ); // pitch, yaw, roll
- anim.animateBy( actor, "rotation", rotation );
+ anim.animateBy( actor, "orientation", rotation );
anim.play();
return true;
}
worldPositionX |FLOAT | ✘ | ✘
worldPositionY |FLOAT | ✘ | ✘
worldPositionZ |FLOAT | ✘ | ✘
- rotation |ROTATION | ✔ | ✔
- worldRotation |ROTATION | ✘ | ✘
+ orientation |ROTATION | ✔ | ✔
+ worldOrientation |ROTATION | ✘ | ✘
scale |VECTOR3 | ✔ | ✔
scaleX |FLOAT | ✔ | ✔
scaleY |FLOAT | ✔ | ✔
name |STRING | ✔ | ✘
sensitive |BOOLEAN | ✔ | ✘
leaveRequired |BOOLEAN | ✔ | ✘
- inheritRotation |BOOLEAN | ✔ | ✘
+ inheritOrientation |BOOLEAN | ✔ | ✘
inheritScale |BOOLEAN | ✔ | ✘
colorMode |NUMBER | ✔ | ✘
positionInheritance |NUMBER | ✔ | ✘
/**
- * Actors rotation
- * @property rotation
+ * Actors orientation
+ * @property orientation
* @type dali Rotation object
*/
-ROTATION
+ORIENTATION
/**
- * Actors world-rotation
- * @property worldRotation
+ * Actors world-orientation
+ * @property worldOrientation
* @type dali Rotation object ( read only)
*/
-WORLD_ROTATION
+WORLD_ORIENTATION
/**
* Actors scale
/**
* Set whether a child actor inherits it's parent's orientation.
* @type Boolean
- * @property inheritRotation
+ * @property inheritOrientation
* @default true
*/
-INHERIT_ROTATION,
+INHERIT_ORIENTATION,
/**
var anim = new dali.Animation(1); // default duration is increased if length of all animations is greater than it.
var animOptions = {
- alpha: "linear",
+ alpha: dali.ALPHA_FUNCTION_LINEAR,
delay: 0.5, // used to delay the start of the animation
duration: 3, // duration of the animation
};
// rotate back to correct orientation
var endRotation = new dali.Rotation(0,0,0);
- animOptions.alpha = "easeInOutSine";
+ animOptions.alpha = dali.ALPHA_FUNCTION_EASE_IN_OUT_SINE;
anim.animateTo(myActor1, "orientation", endRotation, animOptions);
// Delay the myActor2 by a second
animOptions.delay = 0.0;
- animOptions.alpha = "linear";
+ animOptions.alpha = dali.ALPHA_FUNCTION_LINEAR;
anim.animateTo(myActor2, "positionZ", 0, animOptions);
// rotate back to correct orientation
- animOptions.alpha = "easeInOutSine";
+ animOptions.alpha = dali.ALPHA_FUNCTION_EASE_IN_OUT_SINE;
anim.animateTo(myActor2, "orientation", endRotation, animOptions);
return anim;
var shaderAnim = new dali.Animation(duration+delay);
var animOptions = {
- alpha: "doubleEaseInOutSine60",
+ alpha: dali.ALPHA_FUNCTION_EASE_IN_OUT_SINE,
delay: delay,
duration: duration,
};
// also rotate the imageView 90 degrees at the same time.
var rotation = new dali.Rotation(90,0,0,1);
-shaderAnim.animateTo(imageView, "orientation", rotation, { alpha:"linear", duration:duration, delay:delay });
+shaderAnim.animateTo(imageView, "orientation", rotation, { alpha:dali.ALPHA_FUNCTION_LINEAR, duration:duration, delay:delay });
shaderAnim.play();
### Animation alpha functions
-| Name | Description |
-|--------------------|--------------|
-|default |Linear |
-|linear |Linear |
-|square |Square (x^2) |
-|reverse |Reverse linear |
-|easeIn |Speeds up and comes to a sudden stop |
-|easeOut |Sudden start and slows to a gradual stop|
-|easeInOut |Speeds up and slows to a gradual stop|
-|easeInSine |Speeds up and comes to a sudden stop|
-|easeOutSine |Sudden start and slows to a gradual stop|
-|easeInOutSine |Speeds up and slows to a gradual stop |
-|easeInSine33 |Speeds up and comes to a sudden stop |
-|easeOutSine33 |Sudden start and slows to a gradual stop |
-|easeInOutSine33 |Speeds up and slows to a gradual stop |
-|easeInOutSine50 |Speeds up and slows to a gradual stop |
-|easeInOutSine60 |Speeds up and slows to a gradual stop |
-|easeInOutSine70 |Speeds up and slows to a gradual stop |
-|easeInOutSine80 |Speeds up and slows to a gradual stop |
-|easeInOutSine90 |Speeds up and slows to a gradual stop |
-|doubleEaseInOutSine6|Speeds up and slows to a gradual stop, then speeds up again and slows to a gradual stop |
-|easeOutQuint50 |Sudden start and slows to a gradual stop |
-|easeOutQuint80 |Sudden start and slows to a gradual stop |
-|bounce |Sudden start, loses momentum and ** Returns to start position ** |
-|bounceBack |Sudden start, loses momentum and returns to exceed start position ** Returns to start position ** |
-|easeInBack |Slow start, exceed start position and quickly reach destination |
-|easeOutBack |Sudden start, exceed end position and return to a gradual stop|
-|easeInOutBack |Slow start, exceed start position, fast middle, exceed end position and return to a gradual stop|
-|sin |full 360 revolution ** Returns to start position ** |
-|sin2x |full 720 revolution ** Returns to start position ** |
+| Name | Description |
+|----------------------------------|----------------|
+|ALPHA_FUNCTION_DEFAULT |Linear |
+|ALPHA_FUNCTION_LINEAR |Linear |
+|ALPHA_FUNCTION_REVERSE |Reverse linear |
+|ALPHA_FUNCTION_EASE_IN_SQUARE |Speeds up and comes to a sudden stop (Square) |
+|ALPHA_FUNCTION_EASE_OUT_SQUARE |Sudden start and slows to a gradual stop (Square) |
+|ALPHA_FUNCTION_EASE_IN |Speeds up and comes to a sudden stop |
+|ALPHA_FUNCTION_EASE_OUT |Sudden start and slows to a gradual stop|
+|ALPHA_FUNCTION_EASE_IN_OUT |Speeds up and slows to a gradual stop|
+|ALPHA_FUNCTION_EASE_IN_SINE |Speeds up and comes to a sudden stop|
+|ALPHA_FUNCTION_EASE_OUT_SINE |Sudden start and slows to a gradual stop|
+|ALPHA_FUNCTION_EASE_IN_OUT_SINE |Speeds up and slows to a gradual stop |
+|ALPHA_FUNCTION_BOUNCE |Sudden start, loses momentum and ** Returns to start position ** |
+|ALPHA_FUNCTION_SIN |full 360 revolution ** Returns to start position ** |
+|ALPHA_FUNCTION_EASE_OUT_BACK |Sudden start, exceed end position and return to a gradual stop|
|GEOMETRY_TRIANGLE_STRIP | integer value |
|**Property type ** | |
-|PROPERTY_NONE | integer value |
+|PROPERTY_NONE | none |
|PROPERTY_BOOLEAN | integer value |
-|PROPERTY_FLOAT | integer value |
+|PROPERTY_FLOAT | float value |
|PROPERTY_INTEGER | integer value |
-|PROPERTY_VECTOR2 | integer value |
-|PROPERTY_VECTOR3 | integer value |
-|PROPERTY_VECTOR4 | integer value |
-|PROPERTY_MATRIX3 | integer value |
-|PROPERTY_MATRIX | integer value |
-|PROPERTY_RECTANGLE | integer value |
-|PROPERTY_ROTATION | integer value |
-|PROPERTY_STRING | integer value |
-|PROPERTY_ARRAY | integer value |
-|PROPERTY_MAP | integer value |
-|PROPERTY_INVALID_INDEX | integer value |
+|PROPERTY_VECTOR2 | Array[ float, float ] |
+|PROPERTY_VECTOR3 | Array[ float, float, float ] |
+|PROPERTY_VECTOR4 | Array[ float, float, float, float ] |
+|PROPERTY_MATRIX3 | Object |
+|PROPERTY_MATRIX | Object |
+|PROPERTY_RECTANGLE | Object |
+|PROPERTY_ORIENTATION | Object |
+|PROPERTY_STRING | String |
+|PROPERTY_ARRAY | Object |
+|PROPERTY_MAP | Object |
+
+|**Layout dimensions ** | |
+|DIMENSION_WIDTH | integer value |
+|DIMENSION_HEIGHT | integer value |
+
+|**Item layout type ** | |
+|ITEM_LAYOUT_LIST | integer value |
+|ITEM_LAYOUT_GRID | integer value |
+
+|**Scroll direction bias ** | |
+|DIRECTION_BIAS_NONE | integer value |
+|DIRECTION_BIAS_LEFT | integer value |
+|DIRECTION_BIAS_RIGHT | integer value |
+
+|**Animation alpha function ** | |
+|ALPHA_FUNCTION_DEFAULT | integer value |
+|ALPHA_FUNCTION_LINEAR | integer value |
+|ALPHA_FUNCTION_REVERSE | integer value |
+|ALPHA_FUNCTION_EASE_IN_SQUARE | integer value |
+|ALPHA_FUNCTION_EASE_OUT_SQUARE | integer value |
+|ALPHA_FUNCTION_EASE_IN | integer value |
+|ALPHA_FUNCTION_EASE_OUT | integer value |
+|ALPHA_FUNCTION_EASE_IN_OUT | integer value |
+|ALPHA_FUNCTION_EASE_IN_SINE | integer value |
+|ALPHA_FUNCTION_EASE_OUT_SINE | integer value |
+|ALPHA_FUNCTION_EASE_IN_OUT_SINE | integer value |
+|ALPHA_FUNCTION_BOUNCE | integer value |
+|ALPHA_FUNCTION_SIN | integer value |
+|ALPHA_FUNCTION_EASE_OUT_BACK | integer value |
* @class Constants
*/
--- /dev/null
+/**
+ *
+## ItemFactory API
+
+ ItemFactory is for storing the data of {{#crossLink "ItemView"}}ItemView{{/crossLink}}
+ and creating actors for ItemView on request. Each item in ItemView is identified by a
+ unique ID, and has a linear order from 0.
+
+ A JSON file should be provided to ItemFactory which defines the templates of items
+ to be used to create the actors. Multiple templates can be defined in the JSON file
+ for different type of items.
+
+### Simple example of creating a JSON template for items
+
+```
+ {
+ "templates":
+ {
+ "template-item":
+ {
+ "name":"item",
+ "type":"Actor",
+ "position":[0,0,0],
+ "anchorPoint":"TOP_LEFT",
+ "parentOrigin":"TOP_LEFT",
+ "actors":
+ [
+ {
+ "name":"icon",
+ "type":"ImageView",
+ "image":
+ {
+ "rendererType" : "imageRenderer",
+ "imageUrl": "{icon_path}"
+ },
+ "position":[20.0, 0.0, 0.0],
+ "size":[70.0, 70.0, 0.0],
+ "color":[1.0,1.0,1.0,1.0],
+ "anchorPoint":"CENTER_LEFT",
+ "parentOrigin":"CENTER_LEFT",
+ "actors":
+ [
+ {
+ "name":"title",
+ "anchorPoint":"CENTER_LEFT",
+ "parentOrigin":"CENTER_RIGHT",
+ "type":"TextLabel",
+ "position": [30.0, 0.0, 0.0],
+ "size":[200.0, 70.0, 0.0],
+ "pointSize":30,
+ "fontFamily":"HelveticaNeue",
+ "fontStyle":"Bold",
+ "horizontalAlignment":"BEGIN",
+ "verticalAlignment":"CENTER",
+ "textColor": [1.0,0.0,1.0,1.0],
+ "text":"{title_text}"
+ }
+ ]
+ }
+ ]
+ }
+ }
+ }
+```
+
+ The data of items should be provided to ItemFactory as an array of property maps
+ in which each map contains the data for each item, including the template to be used
+ to build the actor and the pairs of key/value to be used to replace the constants
+ defined in the template. The order of property maps in the array represents the actual
+ order of items in ItemView.
+
+ ### Example of defining the data of an ItemView with two items
+
+```
+ var itemViewData = [
+ { "template" : "template-item",
+ "icon_path" : "icon0.png",
+ "title_text" : "Item 0" },
+ { "template" : "template-item",
+ "icon_path" : "icon1.png",
+ "title_text" : "Item 1" }
+ ];
+```
+
+ This means ItemFactory will use the template "template-item" defined in the JSON file
+ to create the item for ItemView and replace the constants "icon_path" and "title_text"
+ in the template with their actual values, e.g. "icon0.png" and "Item 0". Each item can
+ have different template and different data.
+
+ ### Example of creating an ItemFactory with the above JSON template and link it with an ItemView
+
+![ ](../assets/img/item-view/list.png)
+
+```
+ // Define the data of 100 items
+ var itemViewData = [];
+ for (var itemId = 0; itemId < 100; itemId++)
+ {
+ var itemData = {};
+ itemData["template"] = "template-item";
+ itemData["icon_path"] = "icon" + itemId + ".png";
+ itemData["title_text"] = "Item " + itemId;
+ itemViewData[itemId] = itemData;
+ }
+
+ // Create the item factory and set the JSON template file and item view data
+ var itemFactory = new dali.ItemFactory();
+ itemFactory.jsonTemplateFile = "./item-template.json"; // Set the JSON template file
+ itemFactory.data = itemViewData; // Set the ItemView data
+
+ // Create the item view with the given item factory
+ var itemView = new dali.Control("ItemView", itemFactory);
+ itemView.size = [stageSize.x, stageSize.y, 0.0];
+ itemView.parentOrigin = dali.CENTER_LEFT;
+ itemView.anchorPoint = dali.CENTER_LEFT;
+ dali.stage.add( itemView );
+
+ // Add a list layout to ItemView (multiple layouts can be added to the same ItemView)
+ itemView.addLayout(dali.ITEM_LAYOUT_LIST);
+
+ // Set custom item size for the list layout
+ // If set, this will overide the predefined item size in the list layout
+ itemView.setItemSize(0, [350, 100, 0]); // 0 means the first layout added to ItemView
+
+ // Acticate the list layout (which will layout the items as a list)
+ itemView.activateLayout(0, itemView.size); // 0 means the first layout added to ItemView
+```
+
+ ### Example of changing the data of items in ItemView dynamically
+
+```
+ var data = itemFactory.data;
+ data[itemId]["icon_path"] = "new-icon.png";
+ data[itemId]["title_text"] = "New Item";
+ itemFactory.data = data; // ItemView will update the changed items immediately
+```
+
+ @class ItemFactory
+
+*/
+
+/**
+ * Sets the file name of JSON template that contains the templates for items.
+ *
+ * @example
+ * itemFactory.jsonTemplateFile = "item-template.json"; // ItemFactory will look for the template from this JSON file
+ *
+ * @type String
+ * @property jsonTemplateFile
+ */
+JSON_TEMPLATE_FILE
+
+/**
+ * Sets the data of ItemView
+ *
+ * The data is an array of property maps in which each map contains the data
+ * for each item, including the template to be used to build the actor and
+ * the pairs of key/value to be used to replace the constants defined in the
+ * template. The order of property maps in the array represents the actual
+ * order of items in ItemView.
+ *
+ * @example
+ * var itemViewData = [
+ * { "template" : "template-item",
+ * "icon_path" : "icon0.png",
+ * "title_text" : "Item 0" },
+ * { "template" : "template-item",
+ * "icon_path" : "icon1.png",
+ * "title_text" : "Item 1" }
+ * ];
+ *
+ * itemFactory.data = itemViewData; // ItemFactory will create items from this data
+ *
+ * @type Array
+ * @property data
+ */
+DATA
--- /dev/null
+/**
+ *
+## ItemView API
+
+ ItemView is a scrollable layout container with built-in layouts to determine
+ the logical position of each item in a layout.
+
+ Actors are provided from an external {{#crossLink "ItemFactory"}}ItemFactory{{/crossLink}},
+ to display the currently visible items. ItemFactory is for storing the data of ItemView and
+ creating actors for ItemView on request. Each item in ItemView is identified by a unique ID,
+ and has a linear order from 0.
+
+ ### Example of creating an ItemView (see {{#crossLink "ItemFactory"}}ItemFactory{{/crossLink}} API for a full example)
+
+```
+ // Define the data of 100 items
+ var itemViewData = [];
+ for (var itemId = 0; itemId < 100; itemId++)
+ {
+ var itemData = {};
+ itemData["template"] = "template-item";
+ itemData["title_text"] = "Item " + itemId;
+ itemViewData[itemId] = itemData;
+ }
+
+ // Create an item factory and set the JSON template file and item view data
+ var itemFactory = new dali.ItemFactory();
+ itemFactory.jsonTemplateFile = "./item-template.json"; // Set the JSON template file
+ itemFactory.data = itemViewData; // Set the ItemView data
+
+ // Create the item view with the given item factory
+ var itemView = new dali.Control("ItemView", itemFactory);
+ itemView.size = [stageSize.x, stageSize.y, 0.0];
+ itemView.parentOrigin = dali.CENTER_LEFT;
+ itemView.anchorPoint = dali.CENTER_LEFT;
+ dali.stage.add( itemView );
+
+ // Add a scroll bar to ItemView (optional)
+ var scrollBar = new dali.Control("ScrollBar");
+ scrollBar.parentOrigin = dali.TOP_RIGHT;
+ scrollBar.anchorPoint = dali.TOP_RIGHT;
+ scrollBar.widthResizePolicy = "FIT_TO_CHILDREN";
+ scrollBar.heightResizePolicy = "FILL_TO_PARENT";
+ scrollBar.indicatorHeightPolicy = "Fixed";
+ scrollBar.indicatorFixedHeight = 60.0;
+ itemView.add(scrollBar);
+
+ // Add a list layout to ItemView (multiple layouts can be added to the same ItemView)
+ itemView.addLayout(dali.ITEM_LAYOUT_LIST);
+
+ // Set custom item size for the list layout
+ // If set, this will overide the predefined item size in the list layout
+ itemView.setItemSize(0, [350, 100, 0]); // 0 means the first layout added to ItemView
+
+ // Acticate the list layout (which will layout the items as a list)
+ itemView.activateLayout(0, itemView.size); // 0 means the first layout added to ItemView
+```
+
+ @class ItemView
+ @extends Actor
+
+*/
dali.stage.add( imageView );
var animation = new dali.Animation(2.0);
- var animOptions = { alpha:"easeInOutSine", delay:0.5, duration:1.5 };
+ var animOptions = { alpha:dali.ALPHA_FUNCTION_EASE_IN_OUT_SINE, delay:0.5, duration:1.5 };
var forward = new dali.Vector3(1,0,0);
animation.animate( imageView, myPath, forward, animOptions );
--- /dev/null
+/**
+ *
+## ScrollView API
+
+ScrollView is a container where the actors inside it can be scrolled manually
+(via touch or pan gesture) or automatically.
+
+By default, ScrollView can scroll to any position both horizontally and
+vertically and no snapping is enabled.
+
+Scroll mode can be specified to define how ScrollView should handle scrolling
+in X and Y axes respectively (i.e. whether scrolling is enabled horizontally
+or vertically, how scrolling is snapped, and the boundary to prevent ScrollView
+to scroll beyond a certain position in the axes).
+
+![ ](../assets/img/scroll-view/scroll-view.png)
+
+### Example of creating a ScrollView
+
+```
+ // Create a scroll view
+ var scrollView = new dali.Control("ScrollView");
+ var stageSize = dali.stage.getSize();
+ scrollView.size = [stageSize.x, stageSize.y, 0.0];
+ scrollView.parentOrigin = dali.CENTER;
+ scrollView.anchorPoint = dali.CENTER;
+
+ dali.stage.add( scrollView );
+
+ // Add actors to a scroll view with 3 pages
+ var pageRows = 1;
+ var pageColumns = 3;
+ for(var pageRow = 0; pageRow < pageRows; pageRow++)
+ {
+ for(var pageColumn = 0; pageColumn < pageColumns; pageColumn++)
+ {
+ var pageActor = new dali.Control();
+ pageActor.widthResizePolicy = "FILL_TO_PARENT";
+ pageActor.heightResizePolicy = "FILL_TO_PARENT";
+ pageActor.parentOrigin = dali.CENTER;
+ pageActor.anchorPoint = dali.CENTER;
+ pageActor.position = [pageColumn * stageSize.x, pageRow * stageSize.y, 0.0];
+ pageActor.name = "pageActor" + pageColumn;
+
+ // Add images in a 3x4 grid layout for each page
+ var imageRows = 4;
+ var imageColumns = 3;
+ var margin = 10.0;
+ var imageSize = [(stageSize.x / imageColumns) - margin, (stageSize.y / imageRows) - margin, 0.0];
+
+ for(var row = 0; row < imageRows; row++)
+ {
+ for(var column = 0; column < imageColumns;column++)
+ {
+ var imageView = new dali.Control("ImageView");
+ var imageId = row * imageColumns + column;
+ imageView.image = "./image-" + imageId + ".jpg";
+ imageView.parentOrigin = dali.CENTER;
+ imageView.anchorPoint = dali.CENTER;
+ imageView.size = imageSize;
+ imageView.position = [ margin * 0.5 + (imageSize[0] + margin) * column - stageSize.x * 0.5 + imageSize[0] * 0.5,
+ margin * 0.5 + (imageSize[1] + margin) * row - stageSize.y * 0.5 + imageSize[1] * 0.5,
+ 0.0 ];
+ pageActor.add(imageView);
+ var position = imageView.position;
+ }
+ }
+
+ scrollView.add( pageActor );
+ }
+ }
+
+ // Set scroll view to have 3 pages in X axis and allow page snapping,
+ // and also disable scrolling in Y axis.
+ var scrollMode = {
+ xAxisScrollEnabled : true,
+ xAxisSnapToInterval : stageSize.x, // Define the snap points
+ xAxisScrollBoundary : stageSize.x * pageColumns, // i.e. Define 3 pages
+ yAxisScrollEnabled : false
+ }
+
+ scrollView.setScrollMode(scrollMode);
+
+```
+
+ @class ScrollView
+ @extends Actor
+
+*/
$(v8_plugin_dir)/actors/actor-api.cpp \
$(v8_plugin_dir)/actors/layer-api.cpp \
$(v8_plugin_dir)/actors/camera-actor-api.cpp \
+ $(v8_plugin_dir)/controls/control-wrapper.cpp \
+ $(v8_plugin_dir)/controls/item-factory-wrapper.cpp \
+ $(v8_plugin_dir)/controls/item-view-api.cpp \
+ $(v8_plugin_dir)/controls/scroll-view-api.cpp \
$(v8_plugin_dir)/constants/constants-wrapper.cpp \
$(v8_plugin_dir)/animation/animation-api.cpp \
$(v8_plugin_dir)/animation/animation-wrapper.cpp \
namespace // unanmed namespace
{
+
Actor GetActor( v8::Isolate* isolate, const v8::FunctionCallbackInfo<v8::Value>& args )
{
HandleWrapper* handleWrapper = HandleWrapper::Unwrap( isolate, args.This() );
return Actor::DownCast( handleWrapper->mHandle );
}
-} //unanmed namespace
-
-namespace TextLabelApi
-{
- Actor New( const v8::FunctionCallbackInfo< v8::Value >& args )
- {
- return Dali::Toolkit::TextLabel::New();
- }
-}
+} //unanmed namespace
/***************************************
* ACTOR API FUNCTIONS
}
/**
- * Retrieve and child actor by index.
+ * Retrieve a child actor by index.
*
* @for Actor
* @method getChildAt
}
/**
+ * Return the value of negotiated dimension for the given dimension
+ *
+ * @for Actor
+ * @method getRelayoutSize
+ * @param {Integer} dimension The dimension of layout to retrieve (either dali.DIMENSION_WIDTH or dali.DIMENSION_HEIGHT)
+ * @return {Number} The value of the negotiated dimension
+ */
+void ActorApi::GetRelayoutSize( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+ Actor actor = GetActor( isolate, args );
+
+ bool found;
+ int dimension = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "missing dimension parameter");
+ return;
+ }
+
+ args.GetReturnValue().Set( v8::Number::New( isolate, actor.GetRelayoutSize( static_cast<Dimension::Type>(dimension) ) ) );
+}
+
+/**
* Calculate the width of the actor given a height
*
* The natural size is used for default calculation.
namespace V8Plugin
{
-namespace TextLabelApi
-{
- /**
- * Temporary TextView constructor
- */
- Actor New( const v8::FunctionCallbackInfo< v8::Value >& args );
-}
-
namespace ActorApi
{
void SetKeyboardFocusable( const v8::FunctionCallbackInfo< v8::Value >& args );
void IsKeyboardFocusable( const v8::FunctionCallbackInfo< v8::Value >& args );
void GetNaturalSize( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void GetRelayoutSize( const v8::FunctionCallbackInfo< v8::Value >& args );
void GetWidthForHeight( const v8::FunctionCallbackInfo<v8::Value>& args );
void GetHeightForWidth( const v8::FunctionCallbackInfo<v8::Value>& args );
void TranslateBy( const v8::FunctionCallbackInfo< v8::Value >& args );
/**
* Lookup table to match a actor type with a constructor and supported API's.
- * HandleWrapper::ActorType is used to index this table
+ * ActorWrapper::ActorType is used to index this table
*/
const ActorApiStruct ActorApiLookup[]=
{
// ignore. SetSize() use Actor.size
// ignore. GetCurrentSize() use Actor.size
{ "GetNaturalSize", ActorApi::GetNaturalSize, ACTOR_API },
+ { "GetRelayoutSize", ActorApi::GetRelayoutSize, ACTOR_API },
{ "GetWidthForHeight",ActorApi::GetWidthForHeight, ACTOR_API },
{ "GetHeightForWidth",ActorApi::GetHeightForWidth, ACTOR_API },
// ignore. SetPosition(....) use Actor.position
// create an instance of the template
v8::Local<v8::Object> localObject = objectTemplate->NewInstance();
- // create teh actor object
+ // create the actor object
ActorWrapper* pointer = new ActorWrapper( actor, Dali::V8Plugin::DaliWrapper::Get().GetDaliGarbageCollector() );
// assign the JavaScript object to the wrapper.
args.GetReturnValue().Set( localObject );
}
-void ActorWrapper::NewControl( const v8::FunctionCallbackInfo< v8::Value >& args)
-{
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- if( !args.IsConstructCall() )
- {
- DALI_SCRIPT_EXCEPTION( isolate, "constructor called without 'new" );
- return;
- }
-
- bool found( false );
- std::string controlName = V8Utils::GetStringParameter( PARAMETER_0, found, isolate, args );
-
- if( !found )
- {
- DALI_SCRIPT_EXCEPTION( isolate, "missing control name" );
- return;
- }
- Actor control;
- Dali::TypeInfo typeInfo = Dali::TypeRegistry::Get().GetTypeInfo( controlName );
- if( typeInfo ) // handle, check if it has a value
- {
- Dali::BaseHandle handle = typeInfo.CreateInstance();
- if( handle )
- {
- control = Actor::DownCast( handle );
- }
- }
-
- v8::Local<v8::Object> localObject = WrapActor( isolate, control, ACTOR );
-
- args.GetReturnValue().Set( localObject );
-}
-
-
/**
* given an actor type name, e.g. CameraActor returns the type, e.g. ActorWrapper::CAMERA_ACTOR
*/
return ActorWrapper::UNKNOWN_ACTOR;
}
-
-
} // namespace V8Plugin
} // namespace Dali
static void NewActor( const v8::FunctionCallbackInfo< v8::Value >& args);
/**
- * @brief Creates a new Control wrapped inside a Javascript Object.
- * @note: the control type is passed as a parameter e.g. 'TextField'
- * @param[in] args v8 function call arguments interpreted
- */
- static void NewControl( const v8::FunctionCallbackInfo< v8::Value >& args);
-
- /**
* @brief Wraps an actor of a given type
*/
static v8::Handle<v8::Object> WrapActor(v8::Isolate* isolate, Dali::Actor actor,ActorType actorType);
*/
static ActorWrapper::ActorType GetActorType( const std::string& name );
-private:
+protected:
/**
- * Helper to make the actor template
+ * @brief Helper to make the actor template
*
*/
static v8::Handle<v8::ObjectTemplate> MakeDaliActorTemplate( v8::Isolate* isolate, ActorType actorType );
+private:
+
/**
* Helper, get an actor template given an actor type
*/
#include "path-wrapper.h"
// EXTERNAL INCLUDES
-#include <cstring> // for strcmp
#include <dali/integration-api/debug.h>
namespace // un named namespace
{
-// @todo think about alternative ways of passing around
-struct AlphaFuncStruct
-{
- const char* const name;
- AlphaFunction alphaFunc;
-};
-/**
- * Contains a list of alpha functions that can be used.
- */
-const AlphaFuncStruct AlphaFunctionTable[]=
-{
-
- {"default" , AlphaFunction::DEFAULT },
- {"linear" , AlphaFunction::LINEAR },
- {"reverse" , AlphaFunction::REVERSE },
-
- {"easeInSquare" , AlphaFunction::EASE_IN_SQUARE },
- {"easeOutSquare" , AlphaFunction::EASE_OUT_SQUARE },
-
- {"easeIn" , AlphaFunction::EASE_IN },
- {"easeOut" , AlphaFunction::EASE_OUT },
- {"easeInOut" , AlphaFunction::EASE_IN_OUT },
-
- {"easeInSine" , AlphaFunction::EASE_IN_SINE },
- {"easeOutSine" , AlphaFunction::EASE_OUT_SINE },
- {"easeInOutSine" , AlphaFunction::EASE_IN_OUT_SINE },
-
- {"bounce" , AlphaFunction::BOUNCE },
- {"sin" , AlphaFunction::SIN },
- {"easeOutBack" , AlphaFunction::EASE_OUT_BACK },
-
-};
-const unsigned int AlphaFunctionTableCount = sizeof(AlphaFunctionTable)/sizeof(AlphaFunctionTable[0]);
-const char* const DEFAULT_ALPHA_NAME = "default";
-static AlphaFunction DEFAULT_ALPHA_FUNCTION = AlphaFunction::DEFAULT;
-
-
-
-AlphaFunction GetAlphaFunction( const std::string& alphaFuncName )
-{
- // This will normally get called just a few times during the application, so no point in doing anything clever
- for( unsigned int i = 0; i < AlphaFunctionTableCount; i++)
- {
- const AlphaFuncStruct& alphaStruct( AlphaFunctionTable[i] );
-
- if( std::strcmp( alphaStruct.name , alphaFuncName.c_str() ) == 0 )
- {
- return alphaStruct.alphaFunc;
- }
- }
-
- DALI_LOG_ERROR("Failed to find alpha func |%s| \n", alphaFuncName.c_str() );
- return DEFAULT_ALPHA_FUNCTION;
-}
-
-const char* const GetAlphaFunctionName( AlphaFunction alphaFunc )
-{
- // This may get called 3 times during the application, so no point
- // in doing anything clever
-
- for( unsigned int i = 0; i < AlphaFunctionTableCount; i++)
- {
- const AlphaFuncStruct& alphaStruct( AlphaFunctionTable[i] );
-
-
- if( alphaStruct.alphaFunc.GetBuiltinFunction() == alphaFunc.GetBuiltinFunction() )
- {
- return alphaStruct.name;
- }
- }
- return "default";
-}
-
-
struct AnimationParameters
{
AnimationParameters( const Animation& anim)
: propertyIndex( Property::INVALID_INDEX ),
- alphaFunction( DEFAULT_ALPHA_FUNCTION),
+ alphaFunction( AlphaFunction::DEFAULT),
delay( 0.f ),
duration(anim.GetDuration()),
optionsFound( false )
{
v8::Local<v8::Object> obj = options->ToObject();
v8::Local<v8::Value> alphaValue = obj->Get( v8::String::NewFromUtf8( isolate, "alpha" ) );
- if( alphaValue->IsString() )
+ if( alphaValue->IsUint32() )
{
animParams.optionsFound = true;
- std::string alphaName = V8Utils::v8StringToStdString( alphaValue );
- animParams.alphaFunction = GetAlphaFunction( alphaName );
+ animParams.alphaFunction = static_cast<AlphaFunction::BuiltinFunction>(alphaValue->ToUint32()->Value());
}
v8::Local<v8::Value> delayValue = obj->Get( v8::String::NewFromUtf8( isolate, "delay" ) );
// get keyframe.alpha
v8::Handle<v8::Value> alphaValue = keyFrameObject->Get(v8::String::NewFromUtf8( isolate, "alpha"));
- if( alphaValue->IsString() )
+ if( alphaValue->IsUint32() )
{
- std::string alphaName = V8Utils::v8StringToStdString( alphaValue );
- AlphaFunction alphaFunction = GetAlphaFunction( alphaName );
+ AlphaFunction alphaFunction = static_cast<AlphaFunction::BuiltinFunction>(alphaValue->ToUint32()->Value());
keyframes.Add( progress->NumberValue(), value, alphaFunction );
}
else
* Set the default alpha function for an animation.
* @method setDefaultAlphaFunction
* @for Animation
- * @param {string} alpha function
+ * @param {Integer} alpha function
*/
void AnimationApi::SetDefaultAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args )
{
Animation anim = GetAnimation( isolate, args );
bool found( false );
- std::string alphaFunc = V8Utils::GetStringParameter( PARAMETER_0, found, isolate, args );
+ int alphaFunc = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
if( !found )
{
DALI_SCRIPT_EXCEPTION( isolate, "bad parameter" );
}
else
{
- AlphaFunction func = GetAlphaFunction( alphaFunc );
+ AlphaFunction func = static_cast<AlphaFunction::BuiltinFunction>(alphaFunc);
anim.SetDefaultAlphaFunction( func );
}
-
}
/**
* Get the default alpha function for an animation.
* @method getDefaultAlphaFunction
* @for Animation
- * @return {string} alpha function
+ * @return {Integer} alpha function
*/
void AnimationApi::GetDefaultAlphaFunction( const v8::FunctionCallbackInfo<v8::Value>& args )
{
Animation anim = GetAnimation( isolate, args );
- std::string alphaName = GetAlphaFunctionName( anim.GetDefaultAlphaFunction() );
+ AlphaFunction alphaFunc = anim.GetDefaultAlphaFunction();
- args.GetReturnValue().Set( v8::String::NewFromUtf8( isolate, alphaName.c_str() ) );
+ args.GetReturnValue().Set( v8::Integer::New( isolate, alphaFunc.GetBuiltinFunction() ) );
}
/**
targetPropertyIndex = targetActor.GetPropertyIndex( propertyName );
if( targetPropertyIndex == Property::INVALID_INDEX )
{
- targetPropertyIndex = targetActor.GetPropertyIndex( propertyName );
-
- if( targetPropertyIndex == Property::INVALID_INDEX )
- {
- DALI_SCRIPT_EXCEPTION( isolate, "Target property not found" );
- return false;
- }
+ DALI_SCRIPT_EXCEPTION( isolate, "Target property not found" );
+ return false;
}
}
else
sourcePropertyIndex = targetActor.GetPropertyIndex( propertyName );
if( sourcePropertyIndex == Property::INVALID_INDEX )
{
- sourcePropertyIndex = targetActor.GetPropertyIndex( propertyName );
-
- if( sourcePropertyIndex == Property::INVALID_INDEX )
- {
- DALI_SCRIPT_EXCEPTION( isolate, "Source property not found" );
- return false;
+ DALI_SCRIPT_EXCEPTION( isolate, "Source property not found" );
+ return false;
}
- }
}
else
{
#include <dali/public-api/actors/sampling.h>
#include <dali/public-api/render-tasks/render-task.h>
#include <dali/public-api/common/loading-state.h>
-#include <dali/devel-api/rendering/material.h>
+#include <dali/devel-api/rendering/renderer.h>
#include <dali/devel-api/rendering/geometry.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/default-item-layout.h>
+#include <dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view.h>
namespace Dali
{
{ "WRAP_MODE_REPEAT", WrapMode::REPEAT },
{ "WRAP_MODE_MIRRORED_REPEAT", WrapMode::MIRRORED_REPEAT },
- { "MATERIAL_NONE", Material::NONE },
- { "MATERIAL_CULL_BACK", Material::CULL_BACK },
- { "MATERIAL_CULL_FRONT", Material::CULL_FRONT },
- { "MATERIAL_CULL_BACK_AND_FRONT", Material::CULL_BACK_AND_FRONT },
+ { "MATERIAL_NONE", Renderer::NONE },
+ { "MATERIAL_CULL_BACK", Renderer::CULL_BACK },
+ { "MATERIAL_CULL_FRONT", Renderer::CULL_FRONT },
+ { "MATERIAL_CULL_BACK_AND_FRONT", Renderer::CULL_BACK_AND_FRONT },
{ "GEOMETRY_POINTS", Geometry::POINTS },
{ "GEOMETRY_LINES", Geometry::LINES },
{ "PROPERTY_ARRAY", Property::ARRAY },
{ "PROPERTY_MAP", Property::MAP },
{ "PROPERTY_INVALID_INDEX", Property::INVALID_INDEX },
+ { "PROPERTY_READ_ONLY", Property::READ_ONLY },
+ { "PROPERTY_READ_WRITE", Property::READ_WRITE },
+ { "PROPERTY_ANIMATABLE", Property::ANIMATABLE },
+
+ { "DIMENSION_WIDTH", Dimension::WIDTH },
+ { "DIMENSION_HEIGHT", Dimension::HEIGHT },
+
+ { "ITEM_LAYOUT_LIST", Toolkit::DefaultItemLayout::LIST },
+ { "ITEM_LAYOUT_GRID", Toolkit::DefaultItemLayout::GRID },
+
+ { "DIRECTION_BIAS_NONE", Toolkit::DirectionBiasNone },
+ { "DIRECTION_BIAS_LEFT", Toolkit::DirectionBiasLeft },
+ { "DIRECTION_BIAS_RIGHT", Toolkit::DirectionBiasRight },
+
+ { "ALPHA_FUNCTION_DEFAULT", AlphaFunction::DEFAULT },
+ { "ALPHA_FUNCTION_LINEAR", AlphaFunction::LINEAR },
+ { "ALPHA_FUNCTION_REVERSE", AlphaFunction::REVERSE },
+ { "ALPHA_FUNCTION_EASE_IN_SQUARE", AlphaFunction::EASE_IN_SQUARE },
+ { "ALPHA_FUNCTION_EASE_OUT_SQUARE", AlphaFunction::EASE_OUT_SQUARE },
+ { "ALPHA_FUNCTION_EASE_IN", AlphaFunction::EASE_IN },
+ { "ALPHA_FUNCTION_EASE_OUT", AlphaFunction::EASE_OUT },
+ { "ALPHA_FUNCTION_EASE_IN_OUT", AlphaFunction::EASE_IN_OUT },
+ { "ALPHA_FUNCTION_EASE_IN_SINE", AlphaFunction::EASE_IN_SINE },
+ { "ALPHA_FUNCTION_EASE_OUT_SINE", AlphaFunction::EASE_OUT_SINE },
+ { "ALPHA_FUNCTION_EASE_IN_OUT_SINE", AlphaFunction::EASE_IN_OUT_SINE },
+ { "ALPHA_FUNCTION_BOUNCE", AlphaFunction::BOUNCE },
+ { "ALPHA_FUNCTION_SIN", AlphaFunction::SIN },
+ { "ALPHA_FUNCTION_EASE_OUT_BACK", AlphaFunction::EASE_OUT_BACK },
};
const unsigned int EnumTableCount = sizeof(EnumTable)/sizeof(EnumTable[0]);
--- /dev/null
+/*
+ * Copyright (c) 2015 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 <actors/actor-wrapper.h>
+#include "control-wrapper.h"
+
+// EXTERNAL INCLUDES
+#include <dali/public-api/object/type-registry.h>
+
+// INTERNAL INCLUDES
+#include <controls/item-view-api.h>
+#include <controls/scroll-view-api.h>
+#include <v8-utils.h>
+#include <dali-wrapper.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+v8::Persistent<v8::ObjectTemplate> ControlWrapper::mControlTemplate;
+v8::Persistent<v8::ObjectTemplate> ControlWrapper::mItemViewTemplate;
+v8::Persistent<v8::ObjectTemplate> ControlWrapper::mScrollViewTemplate;
+
+Vector< void* > ControlWrapper::mControlGarbageContainer;
+
+namespace
+{
+
+
+/**
+ * pointer to a persistent template handle
+ */
+struct ControlTemplate
+{
+ v8::Persistent<v8::ObjectTemplate>* controlTemplate;
+};
+
+/**
+ * array of templates for each type of control
+ */
+const ControlTemplate ControlTemplateLookup[]=
+{
+ { &ControlWrapper::mControlTemplate }, // CONTROL
+ { &ControlWrapper::mItemViewTemplate }, // ITEMVIEW
+ { &ControlWrapper::mScrollViewTemplate } // SCROLLVIEW
+};
+
+/**
+ * Bitmask of API's that an control can support
+ */
+enum ControlApiBitMask
+{
+ CONTROL_API = 1 << 0,
+ ITEMVIEW_API = 1 << 1,
+ SCROLLVIEW_API = 1 << 2
+};
+
+/**
+ * structure used for the ControlApiLookup.
+ */
+struct ControlApiStruct
+{
+ const char* controlName;
+ ControlWrapper::ControlType controlType;
+ Toolkit::Control (*constructor)( const v8::FunctionCallbackInfo< v8::Value >& args);
+ int supportApis;
+};
+
+/**
+ * Lookup table to match a control type with a constructor and supported API's.
+ * ControlWrapper::ControlType is used to index this table
+ */
+const ControlApiStruct ControlApiLookup[]=
+{
+ {"Control", ControlWrapper::CONTROL, NULL, CONTROL_API },
+ {"ItemView", ControlWrapper::ITEMVIEW, ItemViewApi::New, CONTROL_API | ITEMVIEW_API },
+ {"ScrollView", ControlWrapper::SCROLLVIEW, ScrollViewApi::New, CONTROL_API | SCROLLVIEW_API }
+};
+
+const unsigned int ControlApiLookupCount = sizeof(ControlApiLookup)/sizeof(ControlApiLookup[0]);
+
+
+/**
+ * Creates a control given a type name
+ * Uses the type registry to create an control of the correct type
+ */
+Toolkit::Control CreateControl( const v8::FunctionCallbackInfo< v8::Value >& args,
+ const std::string& typeName )
+{
+ Toolkit::Control control;
+
+ ControlWrapper::ControlType controlType = ControlWrapper::GetControlType( typeName );
+
+ // if we don't currently have specific binding for the given control type,
+ // try to use type registry to create it
+ if( controlType == ControlWrapper::UNKNOWN_CONTROL )
+ {
+ Dali::TypeInfo typeInfo = Dali::TypeRegistry::Get().GetTypeInfo( typeName );
+ if( typeInfo )
+ {
+ Dali::BaseHandle handle = typeInfo.CreateInstance();
+ if( handle )
+ {
+ control = Toolkit::Control::DownCast( handle );
+ if( !control )
+ {
+ DALI_SCRIPT_EXCEPTION( args.GetIsolate(), "Unknown control type" );
+ return Toolkit::Control();
+ }
+ }
+ }
+ }
+ else
+ {
+ // run the constructor for this type of control so it can pull out custom parameters
+ control = (ControlApiLookup[controlType].constructor)( args );
+ }
+
+ return control;
+}
+
+/**
+ * given a control type return what api's it supports
+ */
+int GetControlSupportedApis( ControlWrapper::ControlType type )
+{
+ return ControlApiLookup[type].supportApis;
+}
+
+/**
+ * Used for the ControlFunctionTable to map function names to functions
+ * with for a specific API
+ */
+struct ControlFunctions
+{
+ const char* name; ///< function name
+ void (*function)( const v8::FunctionCallbackInfo< v8::Value >& args);
+ ControlApiBitMask api;
+};
+
+/**
+ * Contains a list of all functions that can be called in
+ * ItemView
+ */
+const ControlFunctions ControlFunctionTable[]=
+{
+
+ /**************************************
+ * ItemView API
+ **************************************/
+ { "GetLayoutCount", ItemViewApi::GetLayoutCount, ITEMVIEW_API },
+ { "AddLayout", ItemViewApi::AddLayout, ITEMVIEW_API },
+ { "RemoveLayout", ItemViewApi::RemoveLayout, ITEMVIEW_API },
+ { "ActivateLayout", ItemViewApi::ActivateLayout, ITEMVIEW_API },
+ { "GetItemSize", ItemViewApi::GetItemSize, ITEMVIEW_API },
+ { "SetItemSize", ItemViewApi::SetItemSize, ITEMVIEW_API },
+ { "ScrollToItem", ItemViewApi::ScrollToItem, ITEMVIEW_API },
+ { "GetItem", ItemViewApi::GetItem, ITEMVIEW_API },
+ { "GetItemId", ItemViewApi::GetItemId, ITEMVIEW_API },
+ { "GetItemsRange", ItemViewApi::GetItemsRange, ITEMVIEW_API },
+
+ /**************************************
+ * ScrollView API
+ **************************************/
+ { "SetScrollMode", ScrollViewApi::SetScrollMode, SCROLLVIEW_API },
+ { "GetCurrentPage", ScrollViewApi::GetCurrentPage, SCROLLVIEW_API },
+ { "ScrollToPosition", ScrollViewApi::ScrollToPosition, SCROLLVIEW_API },
+ { "ScrollToPage", ScrollViewApi::ScrollToPage, SCROLLVIEW_API },
+ { "ScrollToActor", ScrollViewApi::ScrollToActor, SCROLLVIEW_API },
+ { "ScrollToSnapInterval", ScrollViewApi::ScrollToSnapInterval, SCROLLVIEW_API },
+ { "SetScrollFlickAlphaFunction", ScrollViewApi::SetScrollFlickAlphaFunction, SCROLLVIEW_API },
+ { "SetScrollSnapAlphaFunction", ScrollViewApi::SetScrollSnapAlphaFunction, SCROLLVIEW_API },
+ { "SetSnapOvershootAlphaFunction", ScrollViewApi::SetSnapOvershootAlphaFunction, SCROLLVIEW_API },
+
+};
+
+const unsigned int ControlFunctionTableCount = sizeof(ControlFunctionTable)/sizeof(ControlFunctionTable[0]);
+} //un-named space
+
+
+ControlWrapper::ControlWrapper( Toolkit::Control control,
+ GarbageCollectorInterface& gc )
+: ActorWrapper( control, gc ),
+ mControl( control )
+
+{
+}
+
+ControlWrapper::~ControlWrapper()
+{
+ mControlGarbageContainer.Release();
+}
+
+v8::Handle<v8::Object> ControlWrapper::WrapControl(v8::Isolate* isolate, Toolkit::Control control )
+{
+ v8::EscapableHandleScope handleScope( isolate );
+
+ // Check whether the control is a Control
+ ControlWrapper::ControlType controlType = GetControlType( control.GetTypeName() );
+
+ if( controlType == ControlWrapper::UNKNOWN_CONTROL && Toolkit::Control::DownCast(control) )
+ {
+ controlType = ControlWrapper::CONTROL;
+ }
+
+ v8::Local<v8::Object> object = WrapControl( isolate, control, controlType );
+
+ return handleScope.Escape( object );
+}
+
+Toolkit::Control ControlWrapper::GetControl()
+{
+ return mControl;
+}
+
+v8::Handle<v8::Object> ControlWrapper::WrapControl( v8::Isolate* isolate, Toolkit::Control control, ControlType controlType )
+{
+ v8::EscapableHandleScope handleScope( isolate );
+ v8::Local<v8::ObjectTemplate> objectTemplate;
+
+ objectTemplate = GetControlTemplate( isolate, controlType );
+
+ // create an instance of the template
+ v8::Local<v8::Object> localObject = objectTemplate->NewInstance();
+
+ // create the control object
+ ControlWrapper* pointer = new ControlWrapper( control, Dali::V8Plugin::DaliWrapper::Get().GetDaliGarbageCollector() );
+
+ // assign the JavaScript object to the wrapper.
+ // This also stores Dali object, in an internal field inside the JavaScript object.
+ pointer->SetJavascriptObject( isolate, localObject );
+
+ return handleScope.Escape( localObject );
+}
+
+v8::Local<v8::ObjectTemplate> ControlWrapper::GetControlTemplate( v8::Isolate* isolate, ControlWrapper::ControlType type )
+{
+ v8::EscapableHandleScope handleScope( isolate );
+ v8::Local<v8::ObjectTemplate> objectTemplate;
+
+ if( ControlTemplateLookup[type].controlTemplate->IsEmpty() )
+ {
+ objectTemplate = MakeDaliControlTemplate( isolate, type );
+ ControlTemplateLookup[type].controlTemplate->Reset( isolate, objectTemplate );
+ }
+ else
+ {
+ // get the object template
+ objectTemplate = v8::Local<v8::ObjectTemplate>::New( isolate, *ControlTemplateLookup[type].controlTemplate );
+ }
+
+ return handleScope.Escape( objectTemplate );
+}
+
+v8::Handle<v8::ObjectTemplate> ControlWrapper::MakeDaliControlTemplate( v8::Isolate* isolate, ControlType controlType )
+{
+ v8::EscapableHandleScope handleScope( isolate );
+
+ // all the controls support actor APIs
+ v8::Local<v8::ObjectTemplate> objTemplate = ActorWrapper::MakeDaliActorTemplate( isolate, ActorWrapper::ACTOR );
+
+ // find out what API's this control supports
+ int supportApis = GetControlSupportedApis( controlType );
+
+ // add our function properties
+ for( unsigned int i = 0; i < ControlFunctionTableCount; ++i )
+ {
+ const ControlFunctions property = ControlFunctionTable[i];
+
+ // check to see if the control supports a certain type of API
+ // e.g. ItemView will support CONTROL_API and ITEMVIEW_API
+ if( supportApis & property.api )
+ {
+ std::string funcName = V8Utils::GetJavaScriptFunctionName( property.name);
+
+ objTemplate->Set( v8::String::NewFromUtf8( isolate, funcName.c_str() ),
+ v8::FunctionTemplate::New( isolate, property.function ) );
+ }
+ }
+
+ return handleScope.Escape( objTemplate );
+}
+
+void ControlWrapper::NewControl( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ if( !args.IsConstructCall() )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "constructor called without 'new" );
+ return;
+ }
+
+ bool found( false );
+ std::string controlName = V8Utils::GetStringParameter( PARAMETER_0, found, isolate, args );
+
+ Toolkit::Control control;
+ if( found && controlName != ControlApiLookup[0].controlName )
+ {
+ control = CreateControl( args, controlName ); // create the control with the given type
+ }
+ else
+ {
+ control = Toolkit::Control::New(); // no given type, so create the base type of control
+ }
+
+ if( control )
+ {
+ v8::Local<v8::Object> localObject = WrapControl( isolate, control );
+ args.GetReturnValue().Set( localObject );
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "unsupported control type" );
+ }
+}
+
+/**
+ * Given a control type name, e.g. ItemView returns the type, e.g. ControlWrapper::ITEMVIEW
+ */
+ControlWrapper::ControlType ControlWrapper::GetControlType( const std::string& name )
+{
+ for( unsigned int i = 0 ; i < ControlApiLookupCount ; i++ )
+ {
+ if( ControlApiLookup[i].controlName == name )
+ {
+ return ControlApiLookup[i].controlType;
+ }
+ }
+ return ControlWrapper::UNKNOWN_CONTROL;
+}
+
+void ControlWrapper::RegisterGarbage(void* garbage)
+{
+ mControlGarbageContainer.PushBack(garbage);
+}
+
+} // namespace V8Plugin
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_V8PLUGIN_CONTROL_WRAPPER_H__
+#define __DALI_V8PLUGIN_CONTROL_WRAPPER_H__
+
+/*
+ * Copyright (c) 2015 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 INCLUDES
+#include <v8.h>
+#include <dali/public-api/common/dali-vector.h>
+#include <dali-toolkit/public-api/controls/control.h>
+
+// INTERNAL INCLUDES
+#include <actors/actor-wrapper.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+
+/**
+ * Wraps a Dali Control.
+ */
+class ControlWrapper : public ActorWrapper
+{
+
+public:
+
+ /**
+ * Control type used an index.
+ * These enums are used to index the ControlApiLookup table in control-wrapper.cpp.
+ * Any changes made must be reflected in the ControlApiLookup otherwise it may segfault when creating a control
+ */
+ enum ControlType
+ {
+ UNKNOWN_CONTROL = -1,
+ CONTROL = 0,
+ ITEMVIEW = 1,
+ SCROLLVIEW = 2
+ };
+
+ /**
+ * Constructor
+ * @param control DALi control
+ * @param gc garbage collection interface
+ */
+ ControlWrapper( Toolkit::Control control,
+ GarbageCollectorInterface& gc );
+
+ /**
+ * destructor
+ */
+ virtual ~ControlWrapper();
+
+ /**
+ * @brief Creates a new Control wrapped inside a Javascript Object.
+ * @note: the control type is passed as a parameter e.g. 'ItemView'
+ * @param[in] args v8 function call arguments interpreted
+ */
+ static void NewControl( const v8::FunctionCallbackInfo< v8::Value >& args);
+
+ /**
+ * @brief Wraps a control of a given type
+ */
+ static v8::Handle<v8::Object> WrapControl(v8::Isolate* isolate, Toolkit::Control control, ControlType controlType);
+
+ /**
+ * @brief Wraps a control, the type is looked up from the control
+ */
+ static v8::Handle<v8::Object> WrapControl(v8::Isolate* isolate, Toolkit::Control control );
+
+ // The Control ObjectTemplates.
+ static v8::Persistent<v8::ObjectTemplate> mControlTemplate;
+ static v8::Persistent<v8::ObjectTemplate> mItemViewTemplate;
+ static v8::Persistent<v8::ObjectTemplate> mScrollViewTemplate;
+
+ /**
+ * @return the wrapped control
+ */
+ Toolkit::Control GetControl();
+
+ /**
+ * @return the control type
+ */
+ static ControlWrapper::ControlType GetControlType( const std::string& name );
+
+ /**
+ * @brief Register the garbage to be released when the wrapped control is deleted.
+ */
+ static void RegisterGarbage(void* garbage);
+
+private:
+
+ /**
+ * Helper to make the control template
+ */
+ static v8::Handle<v8::ObjectTemplate> MakeDaliControlTemplate( v8::Isolate* isolate, ControlType controlType );
+
+ /**
+ * Helper, get a control template given a control type
+ */
+ static v8::Local<v8::ObjectTemplate> GetControlTemplate( v8::Isolate* isolate, ControlType type );
+
+ Toolkit::Control mControl;
+ static Vector< void* > mControlGarbageContainer;
+
+};
+
+} // namespace V8Plugin
+
+} // namespace Dali
+
+#endif // header
--- /dev/null
+/*
+ * Copyright (c) 2015 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 "item-factory-wrapper.h"
+
+// EXTERNAL INCLUDES
+#include <dali/public-api/common/vector-wrapper.h>
+#include <dali/devel-api/object/weak-handle.h>
+#include <dali-toolkit/devel-api/builder/builder.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-view.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-layout.h>
+
+// INTERNAL INCLUDES
+#include <v8-utils.h>
+#include <dali-wrapper.h>
+#include <shared/api-function.h>
+#include <shared/object-template-helper.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+v8::Persistent<v8::ObjectTemplate> ItemFactoryWrapper::mItemFactoryTemplate;
+
+namespace
+{
+
+typedef std::vector< Property::Map > ItemDataContainer;
+
+// Implementation of ItemFactory for providing actors to ItemView
+class ItemFactory : public Toolkit::ItemFactory
+{
+public:
+
+ /**
+ * Constructor
+ * @param application class, stored as reference
+ */
+ ItemFactory()
+ : mJsonFileLoaded(false),
+ mNumberOfItems(0)
+ {
+ mBuilder = Toolkit::Builder::New();
+ }
+
+ /**
+ * Set the name of the JSON file which defines the templates of items.
+ * @param jsonFile The JSON file
+ */
+ void SetJsonTemplateFile(std::string jsonFile)
+ {
+ if(mJsonFile != jsonFile)
+ {
+ mJsonFile = jsonFile;
+ LoadJsonFile(mJsonFile);
+
+ // Check whether any layout activated in ItemView
+ Toolkit::ItemView itemView = mItemView.GetHandle();
+ if(itemView && itemView.GetActiveLayout() != NULL)
+ {
+ // Refresh ItemView if item templates are changed
+ itemView.Refresh();
+ }
+ }
+ }
+
+ /**
+ * Returns the name of the JSON file.
+ * @return The JSON file name
+ */
+ std::string GetJsonTemplate()
+ {
+ return mJsonFile;
+ }
+
+ /**
+ * Set the data to be used to create new items.
+ *
+ * If ItemView is already created, this will immediately update ItemView with the
+ * new data.
+ *
+ * The data is an array of property maps in which each map contains the data for
+ * each item, including the template to be used to build the actor and the pairs
+ * of key/value to be used to replace the constants defined in the template.
+ * The order of property maps in the array represents the actual order of items
+ * in ItemView.
+ *
+ * @param data The array of property maps
+ */
+ void SetData(ItemDataContainer data)
+ {
+ ItemDataContainer currentData = mData;
+ mData = data;
+ mNumberOfItems = mData.size();
+
+ // Check whether any layout activated in ItemView
+ Toolkit::ItemView itemView = mItemView.GetHandle();
+ if(itemView && itemView.GetActiveLayout() != NULL)
+ {
+ unsigned int currentNumberOfItems = currentData.size();
+ unsigned int newNumberOfItems = data.size();
+
+ // Check whether any items added or deleted from the data
+ // which requires ItemView to be refreshed with the new data
+ if(currentNumberOfItems != newNumberOfItems)
+ {
+ itemView.Refresh();
+ }
+ else
+ {
+ for( unsigned int itemId = 0; itemId < newNumberOfItems; itemId++)
+ {
+ // Check whether the item is already built in ItemView
+ Actor itemActor = itemView.GetItem(itemId);
+ if(itemActor)
+ {
+ // Check if the item needs to be rebuilt
+ if( !V8Utils::IsPropertyMapIdentical(currentData[itemId], data[itemId]) )
+ {
+ // Rebuild the item with the new data
+ Actor newItemActor = NewItem(itemId);
+
+ // Replace the old item with the new one
+ itemView.ReplaceItem( Toolkit::Item( itemId, newItemActor ), 0.0f );
+ }
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * Retrieve the data.
+ * @return the data.
+ */
+ ItemDataContainer GetData()
+ {
+ return mData;
+ }
+
+ /**
+ * Store a weak handle of ItemView in order to access ItemView APIs
+ * from this ItemFactory implementation
+ * @return the data.
+ */
+ void SetItemView(Toolkit::ItemView itemView)
+ {
+ mItemView = itemView;
+ }
+
+public: // From Toolkit::ItemFactory
+
+ /**
+ * Query the number of items available from the factory.
+ * The maximum available item has an ID of GetNumberOfItems() - 1.
+ */
+ virtual unsigned int GetNumberOfItems()
+ {
+ return mJsonFileLoaded ? mNumberOfItems : 0;
+ }
+
+ /**
+ * Create an Actor to represent a visible item.
+ * @param itemId
+ * @return the created actor.
+ */
+ virtual Actor NewItem(unsigned int itemId)
+ {
+ std::string itemTemplate;
+
+ Property::Map constantsMap = mData[itemId];
+ for ( unsigned int i = 0, count = constantsMap.Count(); i < count; ++i )
+ {
+ Property::Value& constantValue = constantsMap.GetValue(i);
+ if(constantsMap.GetKey(i) == "template")
+ {
+ constantValue.Get(itemTemplate);
+ }
+ else
+ {
+ mBuilder.AddConstant( constantsMap.GetKey(i), constantValue );
+ }
+ }
+
+ Actor item = Actor::DownCast( mBuilder.Create(itemTemplate) );
+ return item;
+ }
+
+private:
+
+ /**
+ * Load the JSON file.
+ * @param The JSON file name
+ */
+ void LoadJsonFile(std::string jsonFile)
+ {
+ try
+ {
+ std::string data;
+ V8Utils::GetFileContents(jsonFile, data);
+
+ mBuilder.LoadFromString(data);
+
+ mJsonFileLoaded = true;
+ }
+ catch(...)
+ {
+// printf("invalid JSON data\n");
+ mJsonFileLoaded = false;
+ }
+ }
+
+private:
+
+ std::string mJsonFile;
+ bool mJsonFileLoaded;
+ Toolkit::Builder mBuilder;
+ unsigned int mNumberOfItems;
+ ItemDataContainer mData;
+ WeakHandle< Toolkit::ItemView > mItemView;
+};
+
+} //un-named space
+
+ItemFactoryWrapper::ItemFactoryWrapper( Toolkit::ItemFactory& factory, GarbageCollectorInterface& gc )
+: BaseWrappedObject( BaseWrappedObject::ITEMFACTORY , gc ),
+ mItemFactory( factory )
+{
+}
+
+ItemFactoryWrapper::~ItemFactoryWrapper()
+{
+}
+
+v8::Handle<v8::Object> ItemFactoryWrapper::WrapItemFactory(v8::Isolate* isolate, Toolkit::ItemFactory& factory )
+{
+ v8::EscapableHandleScope handleScope( isolate );
+ v8::Local<v8::ObjectTemplate> objectTemplate;
+
+ objectTemplate = GetItemFactoryTemplate( isolate );
+
+ // create an instance of the template
+ v8::Local<v8::Object> localObject = objectTemplate->NewInstance();
+
+ // create the ItemFactory wrapper
+ ItemFactoryWrapper* pointer = new ItemFactoryWrapper( factory, Dali::V8Plugin::DaliWrapper::Get().GetDaliGarbageCollector() );
+
+ // assign the JavaScript object to the wrapper.
+ pointer->SetJavascriptObject( isolate, localObject );
+
+ return handleScope.Escape( localObject );
+}
+
+v8::Local<v8::ObjectTemplate> ItemFactoryWrapper::GetItemFactoryTemplate( v8::Isolate* isolate)
+{
+ v8::EscapableHandleScope handleScope( isolate );
+ v8::Local<v8::ObjectTemplate> objectTemplate;
+
+ if( mItemFactoryTemplate.IsEmpty() )
+ {
+ objectTemplate = MakeItemFactoryTemplate( isolate );
+ mItemFactoryTemplate.Reset( isolate, objectTemplate );
+ }
+ else
+ {
+ // get the object template
+ objectTemplate = v8::Local<v8::ObjectTemplate>::New( isolate, mItemFactoryTemplate );
+ }
+ return handleScope.Escape( objectTemplate );
+}
+
+v8::Handle<v8::ObjectTemplate> ItemFactoryWrapper::MakeItemFactoryTemplate( v8::Isolate* isolate )
+{
+ v8::EscapableHandleScope handleScope( isolate );
+
+ v8::Local<v8::ObjectTemplate> objTemplate = v8::ObjectTemplate::New();
+
+ objTemplate->SetInternalFieldCount( BaseWrappedObject::FIELD_COUNT );
+
+ // set property setter and getter
+ objTemplate->SetNamedPropertyHandler( ItemFactoryWrapper::PropertyGet, ItemFactoryWrapper::PropertySet);
+
+ return handleScope.Escape( objTemplate );
+}
+
+void ItemFactoryWrapper::NewItemFactory( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate);
+
+ if( !args.IsConstructCall() )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "ItemFactory constructor called without 'new'" );
+ return;
+ }
+
+ Toolkit::ItemFactory* factory = new ItemFactory();
+
+ v8::Local<v8::Object> localObject = WrapItemFactory( isolate, *factory );
+ args.GetReturnValue().Set( localObject );
+}
+
+Toolkit::ItemFactory& ItemFactoryWrapper::GetItemFactoryFromParams( int paramIndex,
+ bool& found,
+ v8::Isolate* isolate,
+ const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ found = false;
+
+ v8::HandleScope handleScope( isolate );
+ BaseWrappedObject* wrappedObject = V8Utils::GetWrappedDaliObjectParameter( paramIndex, BaseWrappedObject::ITEMFACTORY, isolate, args );
+ if( wrappedObject )
+ {
+ found = true;
+ ItemFactoryWrapper* wrapper = static_cast< ItemFactoryWrapper *>(wrappedObject);
+ return wrapper->GetItemFactory();
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "no valid ItemFactory parameter" );
+ Toolkit::ItemFactory* dummyFactory = new ItemFactory();
+ return *dummyFactory; // avoid build error
+ }
+}
+
+ItemFactoryWrapper* ItemFactoryWrapper::Unwrap( v8::Isolate* isolate, v8::Handle< v8::Object> obj)
+{
+ v8::HandleScope handleScope( isolate );
+
+ v8::Local<v8::External> field = v8::Local<v8::External>::Cast( obj->GetInternalField(0) );
+ void* ptr = field->Value();
+ return static_cast< ItemFactoryWrapper *>(ptr);
+}
+
+void ItemFactoryWrapper::PropertyGet( v8::Local<v8::String> propertyName,
+ const v8::PropertyCallbackInfo<v8::Value>& info)
+{
+ v8::Isolate* isolate = info.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ // get the property name
+ std::string name = V8Utils::v8StringToStdString( propertyName );
+
+ if( std::isupper( name[0] ))
+ {
+ return;
+ }
+
+ // unwrap the object
+ ItemFactoryWrapper* itemFactoryWrapper = Unwrap( isolate, info.This() );
+ if( !itemFactoryWrapper )
+ {
+ return;
+ }
+
+ ItemFactory& factory = static_cast<ItemFactory&>( itemFactoryWrapper->GetItemFactory() );
+
+ if( name == "jsonTemplateFile" )
+ {
+ std::string jsonTemplateFile = factory.GetJsonTemplate();
+ info.GetReturnValue().Set(v8::String::NewFromUtf8(isolate, jsonTemplateFile.c_str()));
+ }
+ else if( name == "data" )
+ {
+ ItemDataContainer data = factory.GetData();
+ unsigned int itemCount = data.size();
+
+ v8::Local<v8::Array> array= v8::Array::New( isolate, itemCount );
+ for( unsigned int i = 0; i < itemCount; i++)
+ {
+ v8::Local<v8::Object> mapObject = v8::Object::New( isolate );
+ V8Utils::CreatePropertyMap( isolate, data[i], mapObject );
+
+ array->Set( i, mapObject);
+ }
+
+ info.GetReturnValue().Set(array);
+ }
+ else
+ {
+ std::string error="Invalid property Get for "+name + "\n";
+ DALI_SCRIPT_EXCEPTION( isolate, error );
+ }
+}
+
+void ItemFactoryWrapper::PropertySet( v8::Local<v8::String> propertyName,
+ v8::Local<v8::Value> javaScriptValue,
+ const v8::PropertyCallbackInfo<v8::Value>& info)
+{
+
+ v8::Isolate* isolate = info.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ // get the property name
+ std::string name = V8Utils::v8StringToStdString( propertyName );
+
+ // unwrap the object
+ ItemFactoryWrapper* itemFactoryWrapper = Unwrap( isolate, info.This() );
+ if( !itemFactoryWrapper )
+ {
+ return;
+ }
+
+ ItemFactory& factory = static_cast<ItemFactory&>( itemFactoryWrapper->GetItemFactory() );
+
+ if( name == "jsonTemplateFile" && javaScriptValue->IsString() )
+ {
+ std::string jsonTemplateFile = V8Utils::v8StringToStdString( javaScriptValue );
+ factory.SetJsonTemplateFile(jsonTemplateFile);
+ }
+ else if( name == "data" && javaScriptValue->IsArray() )
+ {
+ v8::Local<v8::Array> array = v8::Local<v8::Array>::Cast(javaScriptValue);
+
+ ItemDataContainer data;
+
+ for( unsigned int i = 0; i < array->Length(); ++i )
+ {
+ v8::Local<v8::Value> itemData = array->Get(i);
+
+ if( itemData->IsObject() )
+ {
+ Dali::Property::Map map = V8Utils::GetPropertyMapFromObject( isolate, itemData->ToObject() );
+ data.push_back(map);
+ }
+ }
+
+ factory.SetData(data);
+ }
+ else
+ {
+ std::string error = "Invalid property Set for " + name + "\n";
+ DALI_SCRIPT_EXCEPTION( isolate, error );
+ }
+}
+
+Toolkit::ItemFactory& ItemFactoryWrapper::GetItemFactory()
+{
+ return mItemFactory;
+}
+
+void ItemFactoryWrapper::SetItemView(Toolkit::ItemFactory& itemFactory, Toolkit::ItemView itemView)
+{
+ ItemFactory& factory = static_cast<ItemFactory&>( itemFactory );
+ factory.SetItemView(itemView);
+}
+
+} // namespace V8Plugin
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_V8PLUGIN_ITEM_FACTORY_WRAPPER_H__
+#define __DALI_V8PLUGIN_ITEM_FACTORY_WRAPPER_H__
+
+/*
+ * Copyright (c) 2015 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 INCLUDES
+#include <v8.h>
+#include <dali/public-api/common/dali-vector.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-factory.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-view.h>
+
+// INTERNAL INCLUDES
+#include <shared/base-wrapped-object.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+
+/**
+ * Wraps a Dali ItemFactory.
+ */
+class ItemFactoryWrapper : public BaseWrappedObject
+{
+
+public:
+
+ /**
+ * Constructor
+ * @param factory DALi ItemFactory
+ * @param gc garbage collection interface
+ */
+ ItemFactoryWrapper( Toolkit::ItemFactory& factory,
+ GarbageCollectorInterface& gc );
+
+ /**
+ * destructor
+ */
+ virtual ~ItemFactoryWrapper();
+
+ /**
+ * @brief Creates a new ItemFactory wrapped inside a Javascript Object.
+ * @note: the item template and data are passed as a parameter e.g. 'template'
+ * @param[in] args v8 function call arguments interpreted
+ */
+ static void NewItemFactory( const v8::FunctionCallbackInfo< v8::Value >& args);
+
+ /**
+ * @brief Wraps an ItemFactory
+ */
+ static v8::Handle<v8::Object> WrapItemFactory(v8::Isolate* isolate, Toolkit::ItemFactory& factory );
+
+ // The ItemFactory ObjectTemplates.
+ static v8::Persistent<v8::ObjectTemplate> mItemFactoryTemplate;
+
+ /**
+ * @brief Helper to get ItemFactory from the JavaScript object held in the given function argument
+ * @param[in] paramIndex Argument index the object is held in
+ * @param[in] found Whether ItemFactory is found in the given function parameter
+ * @param[in] isolate v8 isolated instance
+ * @param[in] args v8 function call arguments interpreted
+ */
+ static Toolkit::ItemFactory& GetItemFactoryFromParams( int paramIndex,
+ bool& found,
+ v8::Isolate* isolate,
+ const v8::FunctionCallbackInfo< v8::Value >& args );
+
+ /**
+ * @brief Helper to store a weak handle of ItemView in the given ItemFactory
+ * @param[in] itemFactory The item factory used to provide items to the given item view
+ * @param[in] itemView The ItemView which uses the given item factory to create items
+ */
+ static void SetItemView(Toolkit::ItemFactory& itemFactory, Toolkit::ItemView itemView);
+
+ /**
+ * @return the wrapped item factory
+ */
+ Toolkit::ItemFactory& GetItemFactory();
+
+private:
+
+ /**
+ * Helper to make the item factory template
+ */
+ static v8::Handle<v8::ObjectTemplate> MakeItemFactoryTemplate( v8::Isolate* isolate );
+
+ /**
+ * Helper, get a item factory template
+ */
+ static v8::Local<v8::ObjectTemplate> GetItemFactoryTemplate( v8::Isolate* isolate );
+
+ /**
+ * @brief get the value for a property for JavaScript object than contains a Dali ItemFactory.
+ * E.g. Get( "data", JavaScript object that wraps a Dali ItemFactory )
+ * @param[in] propertyName property name
+ * @param[in] info reference to PropertyCallbackInfo structure (contains the Javascript
+ * object and the return value).
+ */
+ static void PropertyGet( v8::Local<v8::String> propertyName,
+ const v8::PropertyCallbackInfo<v8::Value>& info);
+
+ /**
+ * @brief Set the value for a property for JavaScript object than contains a Dali ItemFactory.
+ * E.g. Set( "data", itemData, JavaScript object that wraps a Dali ItemFactory)
+ * @param[in] propertyName property name
+ * @param[in] javaScriptValue javascript value to set, this is typically a number
+ * @param[in] info reference to PropertyCallbackInfo structure (contains the Javascript
+ * object).
+ */
+ static void PropertySet( v8::Local<v8::String> propertyName,
+ v8::Local<v8::Value> javaScriptValue,
+ const v8::PropertyCallbackInfo<v8::Value>& info);
+
+
+ /**
+ * @brief Extract a item factory wrapper from a javascript object
+ * @return item factory wrapper
+ */
+ static ItemFactoryWrapper* Unwrap( v8::Isolate* isolate, v8::Handle< v8::Object> obj);
+
+ Toolkit::ItemFactory& mItemFactory;
+
+};
+
+} // namespace V8Plugin
+
+} // namespace Dali
+
+#endif // header
--- /dev/null
+/*
+ * Copyright (c) 2015 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 "item-view-api.h"
+
+// EXTERNAL INCLUDES
+#include <fstream>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-layout.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-factory.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/default-item-layout.h>
+
+// INTERNAL INCLUDES
+#include <v8-utils.h>
+#include <actors/actor-wrapper.h>
+#include <controls/control-wrapper.h>
+#include <controls/item-factory-wrapper.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+namespace // unanmed namespace
+{
+
+Toolkit::ItemView GetItemView( v8::Isolate* isolate, const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ HandleWrapper* handleWrapper = HandleWrapper::Unwrap( isolate, args.This() );
+ return Toolkit::ItemView::DownCast( handleWrapper->mHandle );
+}
+
+} //unanmed namespace
+
+/***************************************
+ * ITEMVIEW API FUNCTIONS
+ ***************************************/
+
+/**
+ * Constructor
+ *
+ * @for ItemView
+ * @constructor
+ * @method ItemView
+ * @return {Object} itemView
+ */
+Toolkit::Control ItemViewApi::New( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ bool found( false );
+ Toolkit::ItemFactory& factory = ItemFactoryWrapper::GetItemFactoryFromParams( 1, found, isolate, args );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid ItemFactory parameter" );
+ return Toolkit::Control();
+ }
+ else
+ {
+ Toolkit::ItemView itemView = Toolkit::ItemView::New(factory);
+ ItemFactoryWrapper::SetItemView(factory, itemView);
+ return itemView;
+ }
+}
+
+/**
+ * Query the number of layouts.
+ *
+ * @for ItemView
+ * @method getLayoutCount
+ * @return {Integer} The number of layouts.
+ */
+void ItemViewApi::GetLayoutCount( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ args.GetReturnValue().Set( v8::Integer::New( isolate, itemView.GetLayoutCount() ) );
+}
+
+/**
+ * Add a layout
+ *
+ * @for ItemView
+ * @method addLayout
+ * @param {Integer} layout The layout to be added
+ * @example
+ * // layout is one of the following
+ * dali.ITEM_LAYOUT_LIST
+ * dali.ITEM_LAYOUT_GRID
+ *
+ * itemView.addLayout( dali.ITEM_LAYOUT_LIST );
+ */
+void ItemViewApi::AddLayout( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int layout = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid layout parameter" );
+ return;
+ }
+
+ Toolkit::ItemLayoutPtr layoutPtr = Toolkit::DefaultItemLayout::New( static_cast<Toolkit::DefaultItemLayout::Type>(layout) );
+ itemView.AddLayout( *layoutPtr );
+}
+
+/**
+ * Remove a layout.
+ *
+ * @for ItemView
+ * @method removeLayout
+ * @param {Integer} layoutIndex The index of the ItemView layouts which must be less than getLayoutCount().
+ */
+void ItemViewApi::RemoveLayout( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int layoutIndex = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid index parameter" );
+ return;
+ }
+
+ itemView.RemoveLayout( layoutIndex );
+}
+
+/**
+ * Activate one of the layouts. This will resize the ItemView and relayout actors within the ItemView.
+ *
+ * @for ItemView
+ * @method activateLayout
+ * @param {Integer} layoutIndex The index of the ItemView layout which must be less than getLayoutCount().
+ * @param {Object} targetSize An array of 3 numbers for the target ItemView and layout size.
+ * @param {Float} [durationSeconds] The time taken to relayout in seconds (0 by default for immediate).
+ */
+void ItemViewApi::ActivateLayout( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int layoutIndex = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid layout index parameter" );
+ return;
+ }
+
+ found = false;
+ Vector3 targetSize = V8Utils::GetVector3Parameter( PARAMETER_1, found, isolate, args );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "Vector3 targetSize size parameter missing" );
+ return;
+ }
+
+ found = false;
+ float durationSeconds = V8Utils::GetFloatParameter( PARAMETER_2, found, isolate, args, 0.0f ); // 0 by default for immediate activation
+
+ itemView.ActivateLayout( layoutIndex, targetSize, durationSeconds );
+}
+
+/**
+ * Retrieve the target size of an item in the given layout.
+ * This will return the default size for the layout unless overridden by calling setLayoutItemSize().
+ *
+ * @for ItemView
+ * @method getItemSize
+ * @param {Integer} layoutIndex The index of the ItemView layout which must be less than getLayoutCount().
+ * @param {Integer} itemId The ID of an item in the layout.
+ * @param {Object} targetLayoutSize An array of 3 numbers for the target ItemView and layout size.
+ * @return {Object} The target size of the item {x, y, z}.
+ */
+void ItemViewApi::GetItemSize( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int layoutIndex = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid layout index parameter" );
+ return;
+ }
+
+ found = false;
+ int itemId = V8Utils::GetIntegerParameter( PARAMETER_1, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid item ID parameter" );
+ return;
+ }
+
+ found = false;
+ Vector3 targetLayoutSize = V8Utils::GetVector3Parameter( PARAMETER_2, found, isolate, args );
+ if( found )
+ {
+ Toolkit::ItemLayoutPtr layoutPtr = itemView.GetLayout(layoutIndex);
+ Vector3 itemSize;
+ layoutPtr->GetItemSize( itemId, targetLayoutSize, itemSize );
+
+ v8::Local<v8::Object> itemSizeObject = v8::Object::New( isolate );
+
+ itemSizeObject->Set( v8::String::NewFromUtf8( isolate, "x" ), v8::Integer::New( isolate, itemSize.width ) );
+ itemSizeObject->Set( v8::String::NewFromUtf8( isolate, "y" ), v8::Integer::New( isolate, itemSize.height ) );
+ itemSizeObject->Set( v8::String::NewFromUtf8( isolate, "z" ), v8::Integer::New( isolate, itemSize.depth ) );
+
+ args.GetReturnValue().Set( itemSizeObject );
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid Vector3 target size parameter" );
+ }
+}
+
+/**
+ * Set the size of the item for the given layout which overrides the default item size for the layout.
+ *
+ * @for ItemView
+ * @method setItemSize
+ * @param {Integer} layoutIndex The index of the ItemView layout which must be less than getLayoutCount().
+ * @param {Object} itemSize An array of 3 numbers for the size of the item.
+ * @example
+ * itemView.setLayoutItemSize( 0, [100.0, 50.0, 0.0] );
+ */
+void ItemViewApi::SetItemSize( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int layoutIndex = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid layout index parameter" );
+ return;
+ }
+
+ found = false;
+ Vector3 itemSize = V8Utils::GetVector3Parameter( PARAMETER_1, found, isolate, args );
+ if( found )
+ {
+ Toolkit::ItemLayoutPtr layoutPtr = itemView.GetLayout(layoutIndex);
+ layoutPtr->SetItemSize( itemSize );
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid item size parameter" );
+ }
+}
+
+/**
+ * Scroll the current layout to a particular item.
+ * If calling this with zero second of duration immediately after calling activateLayout(),
+ * it will not work unless the duration of relayout animation for activateLayout is also
+ * set to zero.
+ *
+ * @for ItemView
+ * @method scrollToItem
+ * @param {Integer} itemId The ID of an item in the layout.
+ * @param {Float} [durationSeconds] How long the scrolling takes in seconds (0 by default for instant scrolling to the particular item).
+ */
+void ItemViewApi::ScrollToItem( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int itemId = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid item Id parameter" );
+ return;
+ }
+
+ found = false;
+ float durationSeconds = V8Utils::GetFloatParameter( PARAMETER_1, found, isolate, args, 0.0f ); // 0 by default for instant scrolling
+
+ itemView.ScrollToItem( itemId, durationSeconds );
+}
+
+/**
+ * Given the Item ID, this returns the accompanying actor.
+ *
+ * @for ItemView
+ * @method getItem
+ * @param {Integer} itemId The Item ID of the actor required.
+ * @return {Object} The Actor corresponding to the Item ID.
+ */
+void ItemViewApi::GetItem( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ int itemId = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 /* default */);
+ if( found )
+ {
+ found = false;
+ Actor actor = itemView.GetItem( itemId );
+ if( actor )
+ {
+ found = true;
+ // wrap the actor
+ v8::Handle < v8::Object > wrappedActor = ActorWrapper::WrapActor( isolate, actor );
+ args.GetReturnValue().Set( wrappedActor );
+ }
+ }
+
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid item ID" );
+ return;
+ }
+}
+
+/**
+ * Returns the Item ID of the specified actor. The actor must be an item of ItemView.
+ *
+ * @for ItemView
+ * @method getItemId
+ * @param {Object} actor The actor whose Item ID is required.
+ * @return {Integer} The Item ID of the item.
+ */
+void ItemViewApi::GetItemId( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ bool found( false );
+ Actor actor = V8Utils::GetActorParameter( 0, found, isolate, args );
+ if( found )
+ {
+ args.GetReturnValue().Set( itemView.GetItemId(actor) );
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid item actor parameter" );
+ return;
+ }
+}
+
+/**
+ * Get the range of items that are currently in ItemView.
+ *
+ * @for ItemView
+ * @method getItemsRange
+ * @return {Object} The range of items in the item ID {begin, end}.
+ */
+void ItemViewApi::GetItemsRange( const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ItemView itemView = GetItemView( isolate, args );
+
+ Toolkit::ItemRange range(0, 0);
+ itemView.GetItemsRange(range);
+
+ v8::Local<v8::Object> itemRangeObject = v8::Object::New( isolate );
+
+ itemRangeObject->Set( v8::String::NewFromUtf8( isolate, "begin" ), v8::Integer::New( isolate, range.begin ) );
+ itemRangeObject->Set( v8::String::NewFromUtf8( isolate, "end" ), v8::Integer::New( isolate, range.end ) );
+
+ args.GetReturnValue().Set( itemRangeObject );
+}
+
+} // namespace V8Plugin
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_V8PLUGIN_ITEM_VIEW_API_H__
+#define __DALI_V8PLUGIN_ITEM_VIEW_API_H__
+
+/*
+ * Copyright (c) 2015 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 INCLUDES
+#include <v8.h>
+#include <dali-toolkit/public-api/controls/scrollable/item-view/item-view.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+namespace ItemViewApi
+{
+
+ /**
+ * constructor
+ */
+ Toolkit::Control New( const v8::FunctionCallbackInfo< v8::Value >& args );
+
+ /**
+ * ItemView API. See item-view.h for description of functions
+ */
+ void GetLayoutCount( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void AddLayout( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void RemoveLayout( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void ActivateLayout( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void GetItemSize( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void SetItemSize( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void ScrollToItem( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void GetItem( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void GetItemId( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void GetItemsRange( const v8::FunctionCallbackInfo< v8::Value >& args);
+
+}; // namespace ItemViewApi
+
+} // namespace V8Plugin
+
+} // namespace Dali
+
+#endif // header __DALI_V8PLUGIN_ITEM_VIEW_API_H__
--- /dev/null
+/*
+ * Copyright (c) 2015 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 "scroll-view-api.h"
+
+// EXTERNAL INCLUDES
+
+// INTERNAL INCLUDES
+#include <v8-utils.h>
+#include <actors/actor-wrapper.h>
+#include <controls/control-wrapper.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+namespace // unanmed namespace
+{
+
+Toolkit::ScrollView GetScrollView( v8::Isolate* isolate, const v8::FunctionCallbackInfo<v8::Value>& args )
+{
+ HandleWrapper* handleWrapper = HandleWrapper::Unwrap( isolate, args.This() );
+ return Toolkit::ScrollView::DownCast( handleWrapper->mHandle );
+}
+
+} //unanmed namespace
+
+/***************************************
+ * SCROLLVIEW API FUNCTIONS
+ ***************************************/
+
+/**
+ * Constructor
+ *
+ * @for ScrollView
+ * @constructor
+ * @method ScrollView
+ * @return {Object} scrollView
+ */
+Toolkit::Control ScrollViewApi::New( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = Toolkit::ScrollView::New();
+ return scrollView;
+}
+
+/**
+ * Set the scroll mode of ScrollView.
+ *
+ * This defines whether scrolling is enabled horizontally or vertically, how
+ * scrolling is snapped, and the boundary in which the scroll view can pan.
+ *
+ * When no specific scroll mode is set, scroll view can scroll to any position
+ * both horizontally and vertically and no snapping is enabled.
+ *
+ * Example of setting the scroll boundary of scroll view in the X axis to
+ * three pages (page size equals to the width of scroll view) and allowing
+ * snapping between pages, and disabling scrolling in the Y axis.
+ *
+ * ```
+ * var scrollMode = {
+ * xAxisScrollEnabled : true,
+ * xAxisSnapToInterval : scrollView.sizeWidth,
+ * xAxisScrollBoundary : scrollView.sizeWidth * 3,
+ * yAxisScrollEnabled : false
+ * }
+ *
+ * scrollView.setScrollMode(scrollMode);
+ * ```
+ *
+ * @for ScrollView
+ * @method setScrollMode
+ * @param {Object} scrollMode
+ * @param {Boolean} scrollMode.xAxisScrollEnabled True if the content can be scrolled in X axis or false if not.
+ * @param {Float} [scrollMode.xAxisSnapToInterval] When set, causes scroll view to snap to multiples of the value of the interval in the X axis while flicking. (by default no snapping)
+ * @param {Float} [scrollMode.xAxisScrollBoundary] When set, causes scroll view unable to scroll beyond the value of the boundary in the X axis (by default no boundary)
+ * @param {Boolean} scrollMode.yAxisScrollEnabled True if the content can be scrolled in Y axis or false if not.
+ * @param {Float} [scrollMode.yAxisSnapToInterval] When set, causes scroll view to snap to multiples of the value of the interval in the Y axis while flicking. (by default no snapping)
+ * @param {Float} [scrollMode.yAxisScrollBoundary] When set, causes scroll view unable to scroll beyond the value of the boundary in the Y axis (by default no boundary)
+ */
+void ScrollViewApi::SetScrollMode( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ v8::Local<v8::Value> scrollMode( args[0] );
+ if( !scrollMode->IsObject() )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid scroll mode parameter" );
+ return;
+ }
+
+ v8::Local<v8::Object> scrollModeObj = scrollMode->ToObject();
+
+ Toolkit::RulerPtr rulerX, rulerY;
+
+ // Check the scroll mode in the X axis
+ bool xAxisScrollEnabled = true;
+ v8::Local<v8::Value> xAxisScrollEnabledValue= scrollModeObj->Get( v8::String::NewFromUtf8( isolate, "xAxisScrollEnabled" ) );
+ if( xAxisScrollEnabledValue->IsBoolean() )
+ {
+ xAxisScrollEnabled = xAxisScrollEnabledValue->ToBoolean()->Value();
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "Missing xAxisScrollEnabled");
+ return;
+ }
+
+ if(!xAxisScrollEnabled)
+ {
+ // Default ruler and disabled
+ rulerX = new Toolkit::DefaultRuler();
+ rulerX->Disable();
+ }
+ else
+ {
+ v8::Local<v8::Value> xAxisSnapToIntervalValue= scrollModeObj->Get( v8::String::NewFromUtf8( isolate, "xAxisSnapToInterval" ) );
+ if( xAxisSnapToIntervalValue->IsNumber() )
+ {
+ // Fixed ruler and enabled
+ float xAxisSnapToInterval = xAxisSnapToIntervalValue->ToNumber()->Value();
+ rulerX = new Toolkit::FixedRuler(xAxisSnapToInterval);
+ }
+ else
+ {
+ // Default ruler and enabled
+ rulerX = new Toolkit::DefaultRuler();
+ }
+
+ v8::Local<v8::Value> xAxisScrollBoundaryValue= scrollModeObj->Get( v8::String::NewFromUtf8( isolate, "xAxisScrollBoundary" ) );
+ if( xAxisScrollBoundaryValue->IsNumber() )
+ {
+ // By default ruler domain is disabled unless set
+ float xAxisScrollBoundary = xAxisScrollBoundaryValue->ToNumber()->Value();
+ rulerX->SetDomain( Toolkit::RulerDomain( 0, xAxisScrollBoundary, true ) );
+ }
+ }
+
+ // Check the scroll mode in the Y axis
+ bool yAxisScrollEnabled = true;
+ v8::Local<v8::Value> yAxisScrollEnabledValue= scrollModeObj->Get( v8::String::NewFromUtf8( isolate, "yAxisScrollEnabled" ) );
+ if( yAxisScrollEnabledValue->IsBoolean() )
+ {
+ yAxisScrollEnabled = yAxisScrollEnabledValue->ToBoolean()->Value();
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "Missing yAxisScrollEnabled");
+ return;
+ }
+
+ if(!yAxisScrollEnabled)
+ {
+ // Default ruler and disabled
+ rulerY = new Toolkit::DefaultRuler();
+ rulerY->Disable();
+ }
+ else
+ {
+ v8::Local<v8::Value> yAxisSnapToIntervalValue= scrollModeObj->Get( v8::String::NewFromUtf8( isolate, "yAxisSnapToInterval" ) );
+ if( yAxisSnapToIntervalValue->IsNumber() )
+ {
+ // Fixed ruler and enabled
+ float yAxisSnapToInterval = yAxisSnapToIntervalValue->ToNumber()->Value();
+ rulerY = new Toolkit::FixedRuler(yAxisSnapToInterval);
+ }
+ else
+ {
+ // Default ruler and enabled
+ rulerY = new Toolkit::DefaultRuler();
+ }
+
+ v8::Local<v8::Value> yAxisScrollBoundaryValue= scrollModeObj->Get( v8::String::NewFromUtf8( isolate, "yAxisScrollBoundary" ) );
+ if( yAxisScrollBoundaryValue->IsNumber() )
+ {
+ // By default ruler domain is disabled unless set
+ float yAxisScrollBoundary = yAxisScrollBoundaryValue->ToNumber()->Value();
+ rulerY->SetDomain( Toolkit::RulerDomain( 0, yAxisScrollBoundary, true ) );
+ }
+ }
+
+ scrollView.SetRulerX(rulerX);
+ scrollView.SetRulerY(rulerY);
+}
+
+/**
+ * Retrieves current scroll page based on the defined snap interval being the
+ * size of one page, and all pages laid out in a grid fashion, increasing from
+ * left to right until the end of the scroll boundary. Pages start from 0 as the
+ * first page.
+ *
+ * If no snap interval is defined, this API will return undefined value.
+ *
+ * @for ScrollView
+ * @method getCurrentPage
+ * @return {Integer} The index of current page in scroll view
+ */
+void ScrollViewApi::GetCurrentPage( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+ args.GetReturnValue().Set( v8::Integer::New( isolate, scrollView.GetCurrentPage() ) );
+}
+
+/**
+ * Scrolls the contents to the given position.
+ *
+ * Position 0,0 is the origin. Increasing X scrolls contents left, while
+ * increasing Y scrolls contents up. If Rulers have been applied to the axes,
+ * then the contents will scroll until reaching the scroll boundary.
+ * Contents will not snap.
+ *
+ * The biasing parameters are provided such that in scenarios with 2 or 2x2 pages
+ * in wrap mode, the application developer can decide whether to scroll left or
+ * right to get to the target page.
+ *
+ * @for ScrollView
+ * @method scrollToPosition
+ * @param {Array} position The position to scroll to.
+ * @param {Float} [durationSeconds] The duration of the scroll animation in seconds (default value is scrollView.scrollSnapDuration)
+ * @param {Integer} [alphaFunction] The alpha function to use.
+ * @param {Integer} [horizontalBias] Whether to bias scrolling to left or right (by default no bias).
+ * @param {Integer} [verticalBias] Whether to bias scrolling to top or bottom (by default no bias).
+ * @example
+ * // scroll direction bias is one of the following
+ * dali.DIRECTION_BIAS_NONE // Don't bias scroll snap
+ * dali.DIRECTION_BIAS_LEFT // Bias scroll snap to Left
+ * dali.DIRECTION_BIAS_RIGHT // Bias scroll snap to Right
+ *
+ * scrollView.scrollToPosition( [150.0, 100.0], 0.5, dali.ALPHA_FUNCTION_EASE_IN_OUT, dali.DIRECTION_BIAS_LEFT, dali.DIRECTION_BIAS_NONE );
+ */
+void ScrollViewApi::ScrollToPosition( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ bool found( false );
+ Vector2 position = V8Utils::GetVector2Parameter( PARAMETER_0, found, isolate, args );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "bad position parameter" );
+ return;
+ }
+
+ float durationSeconds = V8Utils::GetFloatParameter( PARAMETER_1, found, isolate, args, scrollView.GetScrollSnapDuration() );
+
+ AlphaFunction alphaFunction = scrollView.GetScrollSnapAlphaFunction();
+
+ found = false;
+ int alpha = V8Utils::GetIntegerParameter( PARAMETER_2, found, isolate, args, 0 );
+ if(found)
+ {
+ alphaFunction = static_cast<AlphaFunction::BuiltinFunction>(alpha);
+ }
+
+ Toolkit::DirectionBias horizontalBias = static_cast<Toolkit::DirectionBias>( V8Utils::GetIntegerParameter( PARAMETER_3, found, isolate, args, Toolkit::DirectionBiasNone ) );
+ Toolkit::DirectionBias verticalBias = static_cast<Toolkit::DirectionBias>( V8Utils::GetIntegerParameter( PARAMETER_4, found, isolate, args, Toolkit::DirectionBiasNone ) );
+
+ scrollView.ScrollTo( position, durationSeconds, alphaFunction, horizontalBias, verticalBias );
+}
+
+/**
+ * Scrolls the contents to the page with the given index.
+ *
+ * This is based on assumption that the page index starts from 0 and the
+ * position of each page is: [pageIndex * snapToInterval, 0].
+ *
+ * If no snap interval is defined, calling this API will cause unexpected
+ * behaviour.
+ *
+ * The biasing parameter is provided such that in scenarios with 2 pages
+ * in wrap mode, the application developer can decide whether to scroll
+ * left or right to get to the target page.
+ *
+ * @for ScrollView
+ * @method scrollToPage
+ * @param {Integer} pageIndex The index of the page to scroll to.
+ * @param {Float} [durationSeconds] The duration of the scroll animation in seconds (default value is scrollView.scrollSnapDuration)
+ * @param {Integer} [bias] Whether to bias scrolling to left or right (by default no bias).
+ * @example
+ * // scroll direction bias is one of the following
+ * dali.DIRECTION_BIAS_NONE // Don't bias scroll snap
+ * dali.DIRECTION_BIAS_LEFT // Bias scroll snap to Left
+ * dali.DIRECTION_BIAS_RIGHT // Bias scroll snap to Right
+ *
+ * scrollView.scrollToPage( 1, 0.5, dali.DIRECTION_BIAS_RIGHT );
+ */
+void ScrollViewApi::ScrollToPage( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ bool found( false );
+ int pageIndex = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "bad page index parameter" );
+ return;
+ }
+
+ float durationSeconds = V8Utils::GetFloatParameter( PARAMETER_1, found, isolate, args, scrollView.GetScrollSnapDuration() );
+ Toolkit::DirectionBias bias = static_cast<Toolkit::DirectionBias>( V8Utils::GetIntegerParameter( PARAMETER_2, found, isolate, args, Toolkit::DirectionBiasNone ) );
+
+ scrollView.ScrollTo( pageIndex, durationSeconds, bias );
+}
+
+/**
+ * Scrolls the contents such that the given actor appears in the center of
+ * the scroll view.
+ *
+ * The actor must be a direct child of scroll view.
+ *
+ * @for ScrollView
+ * @method scrollToActor
+ * @param {Object} actor The actor to scroll to.
+ * @param {Float} [durationSeconds] The duration of the scroll animation in seconds (default value is scrollView.scrollSnapDuration)
+ * @example
+ * scrollView.scrollToActor( childActor, 0.5 );
+ */
+void ScrollViewApi::ScrollToActor( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ bool found( false );
+ Actor actor = V8Utils::GetActorParameter( 0, found, isolate, args );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid actor parameter" );
+ return;
+ }
+
+ float durationSeconds = V8Utils::GetFloatParameter( PARAMETER_1, found, isolate, args, scrollView.GetScrollSnapDuration() );
+
+ scrollView.ScrollTo( actor, durationSeconds );
+}
+
+/**
+ * Scrolls the content to the nearest snap point as specified by the snap interval.
+ * If already at snap points, it will not scroll.
+ *
+ * @for ScrollView
+ * @method scrollToSnapInterval
+ * @return {Boolean} True if snapping is needed or false if already at snap points
+ * @example
+ * var success = scrollView.scrollToSnapInterval();
+ */
+void ScrollViewApi::ScrollToSnapInterval( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ args.GetReturnValue().Set( v8::Boolean::New( isolate, scrollView.ScrollToSnapPoint() ) );
+}
+
+/**
+ * Set the alpha function of flick animation.
+ *
+ * @for ScrollView
+ * @method setScrollFlickAlphaFunction
+ * @param {Integer} alphaFunction The alpha function to use.
+ * @example
+ * scrollView.setScrollFlickAlphaFunction( dali.ALPHA_FUNCTION_EASE_IN_OUT );
+ */
+void ScrollViewApi::SetScrollFlickAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ bool found( false );
+ int alphaFunction = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid alpha function parameter" );
+ return;
+ }
+ else
+ {
+ scrollView.SetScrollFlickAlphaFunction( static_cast<AlphaFunction::BuiltinFunction>(alphaFunction) );
+ }
+}
+
+/**
+ * Set the alpha function of snap animation.
+ *
+ * @for ScrollView
+ * @method setScrollSnapAlphaFunction
+ * @param {String} alphaFunction The alpha function to use.
+ * @example
+ * scrollView.setScrollSnapAlphaFunction( dali.ALPHA_FUNCTION_EASE_IN_OUT );
+ */
+void ScrollViewApi::SetScrollSnapAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ bool found( false );
+ int alphaFunction = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid alpha function parameter" );
+ return;
+ }
+ else
+ {
+ scrollView.SetScrollSnapAlphaFunction( static_cast<AlphaFunction::BuiltinFunction>(alphaFunction) );
+ }
+}
+
+/**
+ * Set the alpha function of overshoot snap animation.
+ *
+ * @for ScrollView
+ * @method setSnapOvershootAlphaFunction
+ * @param {String} alphaFunction The alpha function to use.
+ * @example
+ * scrollView.setSnapOvershootAlphaFunction( dali.ALPHA_FUNCTION_EASE_IN_OUT );
+ */
+void ScrollViewApi::SetSnapOvershootAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Toolkit::ScrollView scrollView = GetScrollView( isolate, args );
+
+ bool found( false );
+ int alphaFunction = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid alpha function parameter" );
+ return;
+ }
+ else
+ {
+ scrollView.SetSnapOvershootAlphaFunction( static_cast<AlphaFunction::BuiltinFunction>(alphaFunction) );
+ }
+}
+
+} // namespace V8Plugin
+
+} // namespace Dali
--- /dev/null
+#ifndef __DALI_V8PLUGIN_SCROLL_VIEW_API_H__
+#define __DALI_V8PLUGIN_SCROLL_VIEW_API_H__
+
+/*
+ * Copyright (c) 2015 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 INCLUDES
+#include <v8.h>
+#include <dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view.h>
+
+namespace Dali
+{
+
+namespace V8Plugin
+{
+
+namespace ScrollViewApi
+{
+
+ /**
+ * constructor
+ */
+ Toolkit::Control New( const v8::FunctionCallbackInfo< v8::Value >& args );
+
+ /**
+ * ScrollView API. See scroll-view.h for description of functions
+ */
+ void SetScrollMode( const v8::FunctionCallbackInfo< v8::Value >& args);
+ void GetCurrentPage( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void ScrollToPosition( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void ScrollToPage( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void ScrollToActor( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void ScrollToSnapInterval( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void SetScrollFlickAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void SetScrollSnapAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void SetSnapOvershootAlphaFunction( const v8::FunctionCallbackInfo< v8::Value >& args );
+
+}; // namespace ScrollViewApi
+
+} // namespace V8Plugin
+
+} // namespace Dali
+
+#endif // header __DALI_V8PLUGIN_SCROLL_VIEW_API_H__
#include <object/property-value-wrapper.h>
#include <dali/integration-api/debug.h>
#include <actors/actor-wrapper.h>
+#include <controls/control-wrapper.h>
#include <stage/stage-wrapper.h>
#include <image/image-wrapper.h>
#include <animation/linear-constrainer-wrapper.h>
#include <animation/path-constrainer-wrapper.h>
#include <animation/path-wrapper.h>
#include <animation/animation-wrapper.h>
+#include <controls/item-factory-wrapper.h>
#include <events/pan-gesture-detector-wrapper.h>
#include <object/property-buffer-wrapper.h>
#include <rendering/geometry-wrapper.h>
{ "Actor", ActorWrapper::NewActor },
{ "CameraActor", ActorWrapper::NewActor },
{ "Layer", ActorWrapper::NewActor },
- { "Control", ActorWrapper::NewControl },
+ { "Control", ControlWrapper::NewControl },
{ "ResourceImage", ImageWrapper::NewImage },
{ "BufferImage", ImageWrapper::NewImage },
{ "FrameBufferImage", ImageWrapper::NewImage },
{ "Animation", AnimationWrapper::NewAnimation},
+ { "ItemFactory", ItemFactoryWrapper::NewItemFactory},
{ "Shader", ShaderWrapper::NewShader},
{ "Sampler", SamplerWrapper::NewSampler},
{ "Material", MaterialWrapper::NewMaterial},
const ApiFunction HandleFunctionTable[]=
{
{ "RegisterAnimatableProperty", HandleWrapper::RegisterAnimatableProperty },
+ { "RegisterCustomProperty", HandleWrapper::RegisterCustomProperty },
};
const unsigned int HandleFunctionTableCount = sizeof(HandleFunctionTable)/sizeof(HandleFunctionTable[0]);
* @return {integer} The index of the property or dali.PROPERTY_INVALID_INDEX if registration failed
* @example
*
- * var morphPropertyIdex = actor.registerAnimatableProperty("uMorphAmount", 0.0f);
- * var fadeColorPropertyIdex = handle.registerAnimatableProperty("uFadeColor", [1.0, 0.0, 0.0, 1.0]);
+ * var morphPropertyIndex = actor.registerAnimatableProperty("uMorphAmount", 0.0f);
+ * var fadeColorPropertyIndex = handle.registerAnimatableProperty("uFadeColor", [1.0, 0.0, 0.0, 1.0]);
*
*/
void HandleWrapper::RegisterAnimatableProperty( const v8::FunctionCallbackInfo< v8::Value >& args )
}
}
+/**
+ * Register a new custom property.
+ *
+ * The object should support dynamic properties.
+ * Property names must be unused.
+ * Property indices are unique to each registered custom property in a given object.
+ * Properties can be set as non animatable using property attributes.
+ * returns dali.PROPERTY_INVALID_INDEX if registration failed.
+ *
+ * @method registerCustomProperty
+ * @for Handle
+ * @param {string} name The name of the property.
+ * @param {Object} propertyValue The new value of the property.
+ * @param {integer} accessMode The property access mode (writable, animatable etc).
+ * @return {integer} The index of the property or dali.PROPERTY_INVALID_INDEX if registration failed
+ * @example
+ *
+ * // access mode is one of the following
+ * dali.PROPERTY_READ_ONLY
+ * dali.PROPERTY_READ_WRITE
+ * dali.PROPERTY_ANIMATABLE
+ *
+ * var cellIndexPropertyIndex = actor.registerCustomProperty("cellIndex", 2, dali.PROPERTY_READ_WRITE);
+ * var myCustomPropertyIndex = handle.registerCustomProperty("myCustomProperty", [10.0, 25.0, 0.0], dali.PROPERTY_READ_ONLY);
+ *
+ */
+void HandleWrapper::RegisterCustomProperty( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ // unwrap the object
+ HandleWrapper* handleWrapper = Unwrap( isolate, args.This() );
+ if( !handleWrapper )
+ {
+ return;
+ }
+
+ Handle handle = handleWrapper->mHandle;
+
+ bool found( false );
+ std::string propertyName = V8Utils::GetStringParameter( PARAMETER_0, found, isolate, args );
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "bad property name parameter" );
+ return;
+ }
+
+ found = false;
+ Dali::Property::Value daliPropertyValue = V8Utils::GetPropertyValueParameter(PARAMETER_1, found, isolate, args );
+ if( !found || Dali::Property::NONE == daliPropertyValue.GetType() )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "bad property value parameter" );
+ return;
+ }
+
+ found = false;
+ int accessMode = V8Utils::GetIntegerParameter( PARAMETER_2, found, isolate, args, 0 /* default */);
+ if( !found )
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid access mode parameter" );
+ return;
+ }
+ else
+ {
+ args.GetReturnValue().Set( v8::Integer::New( isolate, handle.RegisterProperty( propertyName, daliPropertyValue, static_cast<Property::AccessMode>(accessMode) ) ) );
+ }
+}
+
} // namespace V8Plugin
} // namespace Dali
*/
static void RegisterAnimatableProperty( const v8::FunctionCallbackInfo< v8::Value >& args );
+ /**
+ * @brief Register a custom property for a JavaScript object that
+ * contains a Dali Handle.
+ * @param[in] args v8 function call arguments interpreted
+ */
+ static void RegisterCustomProperty( const v8::FunctionCallbackInfo< v8::Value >& args );
+
Handle GetHandle() { return mHandle; }
Handle mHandle;
ConnectionTracker mConnectionTracker;
args.GetReturnValue().Set( v8::Integer::New( isolate, material.GetNumberOfTextures() ) );
}
-/**
- * Set the culling mode for this material
- *
- * @method setFaceCullingMode
- * @for Material
- * @param {integer} cullingMode The culling mode for this material
- * @example
- * // face culling mode is one of the following
- * dali.MATERIAL_NONE // None of the faces should be culled
- * dali.MATERIAL_CULL_BACK // Cull back face, back face should never be shown
- * dali.MATERIAL_CULL_FRONT // Cull front face, back face should never be shown
- * dali.MATERIAL_CULL_BACK_AND_FRONT // Cull back and front faces, if the geometry is composed of triangles none of the faces will be shown
- *
- * material.setFaceCullingMode( dali.MATERIAL_NONE );
- */
-void MaterialApi::SetFaceCullingMode( const v8::FunctionCallbackInfo< v8::Value >& args )
-{
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- bool found( false );
- int mode = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0);
- if( !found )
- {
- DALI_SCRIPT_EXCEPTION( isolate, "invalid cullingMode parameter" );
- }
- else
- {
- material.SetFaceCullingMode( static_cast<Material::FaceCullingMode>(mode) );
- }
-}
-
-/**
- * Set the blending mode.
- *
- * If blending is disabled (BLENDING_OFF) fade in and fade out animations do not work.
- *
- * @for Material
- * @method setBlendMode
- * @param { integer } mode The blending mode.
- * @example
- * // blend mode is one of the following
- * dali.BLENDING_OFF // Blending is disabled.
- * dali.BLENDING_AUTO // Blending is enabled if there is alpha channel.
- * dali.BLENDING_ON // Blending is enabled.
- *
- * material.setBlendMode( dali.BLENDING_AUTO );
- */
-void MaterialApi::SetBlendMode( const v8::FunctionCallbackInfo< v8::Value >& args )
-{
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- bool found( false );
- int mode = V8Utils::GetIntegerParameter( PARAMETER_0, found, isolate, args, 0 );
- if( !found )
- {
- DALI_SCRIPT_EXCEPTION( isolate, "invalid blendMode parameter" );
- }
- else
- {
- material.SetBlendMode( static_cast<Dali::BlendingMode::Type>( mode ) );
- }
-}
-
-/**
- * Retrieves the blending mode.
- *
- * @for Material
- * @method getBlendMode
- * @return { integer } blendMode
- * @example returns one of the following:
- *
- * dali.BLENDING_OFF // Blending is disabled.
- * dali.BLENDING_AUTO // Blending is enabled if there is alpha channel.
- * dali.BLENDING_ON // Blending is enabled.
- */
-void MaterialApi::GetBlendMode( const v8::FunctionCallbackInfo<v8::Value>& args )
-{
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- args.GetReturnValue().Set( v8::Integer::New( isolate, material.GetBlendMode() ) );
-}
-
-/**
- * Specify the pixel arithmetic used when the actor is blended.
- *
- * @for Material
- * @method setBlendFunc
- * @param {integer} srcFactorRgb Source Blending RGB
- * @param {integer} destFactorRgb Destination Blending RGB
- * @param {integer} srcFactorAlpha Source Blending Alpha
- * @param {integer} destFactorAlpha Destinatino Blending Alpha
- * @example
- * //blending constants
- * dali.BLEND_FACTOR_ZERO
- * dali.BLEND_FACTOR_ONE
- * dali.BLEND_FACTOR_SRC_COLOR
- * dali.BLEND_FACTOR_ONE_MINUS_SRC_COLOR
- * dali.BLEND_FACTOR_SRC_ALPHA
- * dali.BLEND_FACTOR_ONE_MINUS_SRC_ALPHA
- * dali.BLEND_FACTOR_DST_ALPHA
- * dali.BLEND_FACTOR_ONE_MINUS_DST_ALPHA
- * dali.BLEND_FACTOR_DST_COLOR
- * dali.BLEND_FACTOR_ONE_MINUS_DST_COLOR
- * dali.BLEND_FACTOR_SRC_ALPHA_SATURATE
- * dali.BLEND_FACTOR_CONSTANT_COLOR
- * dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_COLOR
- * dali.BLEND_FACTOR_CONSTANT_ALPHA
- * dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_ALPHA
- *
- * material.setBlendFunc( dali.BLEND_FACTOR_CONSTANT_COLOR, dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_COLOR,
- * dali.BLEND_FACTOR_CONSTANT_ALPHA, dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_ALPHA );
- */
-void MaterialApi::SetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args )
-{
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- int params[4];
- bool foundAllParams(false);
- V8Utils::ReadIntegerArguments( foundAllParams, ¶ms[0], 4, args, 0 );
- if( foundAllParams )
- {
- material.SetBlendFunc( static_cast< Dali::BlendingFactor::Type>(params[0]),
- static_cast< Dali::BlendingFactor::Type>(params[1]),
- static_cast< Dali::BlendingFactor::Type>(params[2]),
- static_cast< Dali::BlendingFactor::Type>(params[3]) );
- }
- else
- {
- DALI_SCRIPT_EXCEPTION( isolate, "invalid blendFunc parameter");
- }
-}
-
-/**
- * Query the pixel arithmetic used when the actor is blended.
- *
- * @for Material
- * @method getBlendFunc
- * @return {Object} Blend properties
- * @example Blend properties object has 4 fields
- *
- * blendProperties.sourceRgb // source rgb enum
- * blendProperties.destinationRgb // destination rgb enum
- * blendProperties.sourceAlpha source // alpha enum
- * blendProperties.destinationAlpha // destination alpha enum
- */
-void MaterialApi::GetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args )
-{
- // Pass by reference doesn't work in Javascript
- // For now just return a vector 4...
-
- BlendingFactor::Type srcFactorRgb, destFactorRgb, srcFactorAlpha, destFactorAlpha;
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- material.GetBlendFunc( srcFactorRgb, destFactorRgb, srcFactorAlpha, destFactorAlpha );
-
- v8::Local<v8::Object> blendProperties = v8::Object::New( isolate );
-
- blendProperties->Set( v8::String::NewFromUtf8( isolate, "sourceRgb" ), v8::Integer::New( isolate, srcFactorRgb) );
- blendProperties->Set( v8::String::NewFromUtf8( isolate, "destinationRgb" ), v8::Integer::New( isolate, destFactorRgb ) );
- blendProperties->Set( v8::String::NewFromUtf8( isolate, "sourceAlpha" ), v8::Integer::New( isolate, srcFactorAlpha ) );
- blendProperties->Set( v8::String::NewFromUtf8( isolate, "destinationAlpha" ), v8::Integer::New( isolate, destFactorAlpha ) );
-
- args.GetReturnValue().Set( blendProperties );
-}
-
-/**
- * Specify the equation used when the actor is blended.
- *
- * @for Material
- * @method setBlendEquation
- * @param { integer } equationRgb The equation used for combining red, green, and blue components.
- * @param { integer } equationAlpha The equation used for combining the alpha component.
- * @example
- * // blend equation is one of the following
- * dali.BLEND_EQUATION_ADD
- * dali.BLEND_EQUATION_SUBTRACT
- * dali.BLEND_EQUATION_REVERSE_SUBTRACT
- *
- * material.setBlendEquation( dali.BLEND_EQUATION_ADD, dali.BLEND_EQUATION_REVERSE_SUBTRACT );
- */
-void MaterialApi::SetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args )
-{
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- int params[2];
- bool foundAllParams(false);
- V8Utils::ReadIntegerArguments( foundAllParams, ¶ms[0], 2, args, 0 );
- if( foundAllParams )
- {
- material.SetBlendEquation( static_cast< BlendingEquation::Type>(params[0]), static_cast< BlendingEquation::Type>(params[1]) );
- }
- else
- {
- DALI_SCRIPT_EXCEPTION( isolate, "invalid BlendEquation parameter");
- }
-}
-
-/**
- * Query the equation used when the actor is blended.
- *
- * @for Material
- * @method getBlendEquation
- * @return {Object} Blend equations
- * @example Blend equations object has 2 fields
- *
- * blendEquations.equationRgb // equation used for combining rgb components
- * blendEquations.equationAlpha // equation used for combining alpha components
- */
-void MaterialApi::GetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args )
-{
- // Pass by reference doesn't work in Javascript
- // For now just return a vector 2...
-
- BlendingEquation::Type equationRgb, equationAlpha;
- v8::Isolate* isolate = args.GetIsolate();
- v8::HandleScope handleScope( isolate );
-
- Material material = GetMaterial( isolate, args );
-
- material.GetBlendEquation( equationRgb, equationAlpha );
-
- v8::Local<v8::Object> blendEquations = v8::Object::New( isolate );
-
- blendEquations->Set( v8::String::NewFromUtf8( isolate, "equationRgb" ), v8::Integer::New( isolate, equationRgb) );
- blendEquations->Set( v8::String::NewFromUtf8( isolate, "equationAlpha" ), v8::Integer::New( isolate, equationAlpha ) );
-
- args.GetReturnValue().Set( blendEquations );
-}
-
} // namespace V8Plugin
} // namespace Dali
void SetTextureUniformName( const v8::FunctionCallbackInfo< v8::Value >& args );
void GetTextureIndex( const v8::FunctionCallbackInfo< v8::Value >& args );
void GetNumberOfTextures( const v8::FunctionCallbackInfo< v8::Value >& args );
- void SetFaceCullingMode( const v8::FunctionCallbackInfo< v8::Value >& args );
- void SetBlendMode( const v8::FunctionCallbackInfo< v8::Value >& args );
- void GetBlendMode( const v8::FunctionCallbackInfo< v8::Value >& args );
- void SetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args );
- void GetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args );
- void SetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args );
- void GetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args );
}; // namespace MaterialApi
{ "SetTextureUniformName" , MaterialApi::SetTextureUniformName },
{ "GetTextureIndex" , MaterialApi::GetTextureIndex },
{ "GetNumberOfTextures" , MaterialApi::GetNumberOfTextures },
- { "SetFaceCullingMode" , MaterialApi::SetFaceCullingMode },
- { "SetBlendMode" , MaterialApi::SetBlendMode },
- { "GetBlendMode" , MaterialApi::GetBlendMode },
- { "SetBlendFunc" , MaterialApi::SetBlendFunc },
- { "GetBlendFunc" , MaterialApi::GetBlendFunc },
- { "SetBlendEquation" , MaterialApi::SetBlendEquation },
- { "GetBlendEquation" , MaterialApi::GetBlendEquation },
};
const unsigned int MaterialFunctionTableCount = sizeof(MaterialFunctionTable)/sizeof(MaterialFunctionTable[0]);
args.GetReturnValue().Set( localObject );
}
+/**
+ * Specify the pixel arithmetic used when the actor is blended.
+ *
+ * @for Renderer
+ * @method setBlendFunc
+ * @param {integer} srcFactorRgb Source Blending RGB
+ * @param {integer} destFactorRgb Destination Blending RGB
+ * @param {integer} srcFactorAlpha Source Blending Alpha
+ * @param {integer} destFactorAlpha Destination Blending Alpha
+ * @example
+ * //blending constants
+ * dali.BLEND_FACTOR_ZERO
+ * dali.BLEND_FACTOR_ONE
+ * dali.BLEND_FACTOR_SRC_COLOR
+ * dali.BLEND_FACTOR_ONE_MINUS_SRC_COLOR
+ * dali.BLEND_FACTOR_SRC_ALPHA
+ * dali.BLEND_FACTOR_ONE_MINUS_SRC_ALPHA
+ * dali.BLEND_FACTOR_DST_ALPHA
+ * dali.BLEND_FACTOR_ONE_MINUS_DST_ALPHA
+ * dali.BLEND_FACTOR_DST_COLOR
+ * dali.BLEND_FACTOR_ONE_MINUS_DST_COLOR
+ * dali.BLEND_FACTOR_SRC_ALPHA_SATURATE
+ * dali.BLEND_FACTOR_CONSTANT_COLOR
+ * dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_COLOR
+ * dali.BLEND_FACTOR_CONSTANT_ALPHA
+ * dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_ALPHA
+ *
+ * renderer.setBlendFunc( dali.BLEND_FACTOR_CONSTANT_COLOR, dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_COLOR,
+ * dali.BLEND_FACTOR_CONSTANT_ALPHA, dali.BLEND_FACTOR_ONE_MINUS_CONSTANT_ALPHA );
+ */
+void RendererApi::SetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Renderer renderer = GetRenderer( isolate, args );
+
+ int params[4];
+ bool foundAllParams(false);
+ V8Utils::ReadIntegerArguments( foundAllParams, ¶ms[0], 4, args, 0 );
+ if( foundAllParams )
+ {
+ renderer.SetBlendFunc( static_cast< Dali::BlendingFactor::Type>(params[0]),
+ static_cast< Dali::BlendingFactor::Type>(params[1]),
+ static_cast< Dali::BlendingFactor::Type>(params[2]),
+ static_cast< Dali::BlendingFactor::Type>(params[3]) );
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid blendFunc parameter");
+ }
+}
+
+/**
+ * Query the pixel arithmetic used when the actor is blended.
+ *
+ * @for Renderer
+ * @method getBlendFunc
+ * @return {Object} Blend properties
+ * @example Blend properties object has 4 fields
+ *
+ * blendProperties.sourceRgb // source rgb enum
+ * blendProperties.destinationRgb // destination rgb enum
+ * blendProperties.sourceAlpha source // alpha enum
+ * blendProperties.destinationAlpha // destination alpha enum
+ */
+void RendererApi::GetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ // Pass by reference doesn't work in Javascript
+ // For now just return a vector 4...
+
+ BlendingFactor::Type srcFactorRgb, destFactorRgb, srcFactorAlpha, destFactorAlpha;
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Renderer renderer = GetRenderer( isolate, args );
+
+ renderer.GetBlendFunc( srcFactorRgb, destFactorRgb, srcFactorAlpha, destFactorAlpha );
+
+ v8::Local<v8::Object> blendProperties = v8::Object::New( isolate );
+
+ blendProperties->Set( v8::String::NewFromUtf8( isolate, "sourceRgb" ), v8::Integer::New( isolate, srcFactorRgb) );
+ blendProperties->Set( v8::String::NewFromUtf8( isolate, "destinationRgb" ), v8::Integer::New( isolate, destFactorRgb ) );
+ blendProperties->Set( v8::String::NewFromUtf8( isolate, "sourceAlpha" ), v8::Integer::New( isolate, srcFactorAlpha ) );
+ blendProperties->Set( v8::String::NewFromUtf8( isolate, "destinationAlpha" ), v8::Integer::New( isolate, destFactorAlpha ) );
+
+ args.GetReturnValue().Set( blendProperties );
+}
+
+/**
+ * Specify the equation used when the actor is blended.
+ *
+ * @for Renderer
+ * @method setBlendEquation
+ * @param { integer } equationRgb The equation used for combining red, green, and blue components.
+ * @param { integer } equationAlpha The equation used for combining the alpha component.
+ * @example
+ * // blend equation is one of the following
+ * dali.BLEND_EQUATION_ADD
+ * dali.BLEND_EQUATION_SUBTRACT
+ * dali.BLEND_EQUATION_REVERSE_SUBTRACT
+ *
+ * renderer.setBlendEquation( dali.BLEND_EQUATION_ADD, dali.BLEND_EQUATION_REVERSE_SUBTRACT );
+ */
+void RendererApi::SetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Renderer renderer = GetRenderer( isolate, args );
+
+ int params[2];
+ bool foundAllParams(false);
+ V8Utils::ReadIntegerArguments( foundAllParams, ¶ms[0], 2, args, 0 );
+ if( foundAllParams )
+ {
+ renderer.SetBlendEquation( static_cast< BlendingEquation::Type>(params[0]), static_cast< BlendingEquation::Type>(params[1]) );
+ }
+ else
+ {
+ DALI_SCRIPT_EXCEPTION( isolate, "invalid BlendEquation parameter");
+ }
+}
+
+/**
+ * Query the equation used when the actor is blended.
+ *
+ * @for Renderer
+ * @method getBlendEquation
+ * @return {Object} Blend equations
+ * @example Blend equations object has 2 fields
+ *
+ * blendEquations.equationRgb // equation used for combining rgb components
+ * blendEquations.equationAlpha // equation used for combining alpha components
+ */
+void RendererApi::GetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args )
+{
+ // Pass by reference doesn't work in Javascript
+ // For now just return a vector 2...
+
+ BlendingEquation::Type equationRgb, equationAlpha;
+ v8::Isolate* isolate = args.GetIsolate();
+ v8::HandleScope handleScope( isolate );
+
+ Renderer renderer = GetRenderer( isolate, args );
+
+ renderer.GetBlendEquation( equationRgb, equationAlpha );
+
+ v8::Local<v8::Object> blendEquations = v8::Object::New( isolate );
+
+ blendEquations->Set( v8::String::NewFromUtf8( isolate, "equationRgb" ), v8::Integer::New( isolate, equationRgb) );
+ blendEquations->Set( v8::String::NewFromUtf8( isolate, "equationAlpha" ), v8::Integer::New( isolate, equationAlpha ) );
+
+ args.GetReturnValue().Set( blendEquations );
+}
+
} // namespace V8Plugin
} // namespace Dali
void GetGeometry( const v8::FunctionCallbackInfo< v8::Value >& args );
void SetMaterial( const v8::FunctionCallbackInfo< v8::Value >& args );
void GetMaterial( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void SetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void GetBlendFunc( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void SetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args );
+ void GetBlendEquation( const v8::FunctionCallbackInfo< v8::Value >& args );
}; // namespace RendererApi
{ "GetGeometry" , RendererApi::GetGeometry },
{ "SetMaterial" , RendererApi::SetMaterial },
{ "GetMaterial" , RendererApi::GetMaterial },
+ { "SetBlendFunc" , RendererApi::SetBlendFunc },
+ { "GetBlendFunc" , RendererApi::GetBlendFunc },
+ { "SetBlendEquation" , RendererApi::SetBlendEquation },
+ { "GetBlendEquation" , RendererApi::GetBlendEquation },
};
const unsigned int RendererFunctionTableCount = sizeof(RendererFunctionTable)/sizeof(RendererFunctionTable[0]);
IMAGE_ATTRIBUTES,
ACTOR,
ACTOR_PROPERTY,
+ ITEMVIEW,
+ ITEMFACTORY,
+ SCROLLVIEW,
RENDER_TASK,
RENDER_TASK_LIST,
TIMER,
}
}
+bool IsPropertyMapIdentical(Property::Map map1, Property::Map map2)
+{
+ bool dirty = false;
+
+ // Compare number of properties
+ if ( map1.Count() != map2.Count() )
+ {
+ dirty = true;
+ }
+ else
+ {
+ for ( unsigned int i = 0, count = map1.Count(); i < count; ++i )
+ {
+ // Compare the key first
+ if(map1.GetKey(i) != map2.GetKey(i))
+ {
+ dirty = true;
+ }
+ else
+ {
+ Property::Value& value = map1.GetValue(i);
+ Property::Value& newValue = map2.GetValue(i);
+
+ // Compare the value type
+ if(value.GetType() != newValue.GetType())
+ {
+ dirty = true;
+ }
+ else
+ {
+ // Compare the value
+ switch( value.GetType() )
+ {
+ case Property::BOOLEAN:
+ {
+ dirty = ( value.Get<bool>() != newValue.Get<bool>() );
+ break;
+ }
+ case Property::FLOAT:
+ {
+ dirty = ( value.Get<float>() != newValue.Get<float>() );
+ break;
+ }
+ case Property::INTEGER:
+ {
+ dirty = ( value.Get<int>() != newValue.Get<int>() );
+ break;
+ }
+ case Property::RECTANGLE:
+ {
+ dirty = ( value.Get< Rect<int> >() != newValue.Get< Rect<int> >() );
+ break;
+ }
+ case Property::VECTOR2:
+ {
+ dirty = ( value.Get<Vector2>() != newValue.Get<Vector2>() );
+ break;
+ }
+ case Property::VECTOR3:
+ {
+ dirty = ( value.Get<Vector3>() != newValue.Get<Vector3>() );
+ break;
+ }
+ case Property::VECTOR4:
+ {
+ dirty = ( value.Get<Vector4>() != newValue.Get<Vector4>() );
+ break;
+ }
+ case Property::MATRIX3:
+ {
+ dirty = ( value.Get<Matrix3>() != newValue.Get<Matrix3>() );
+ break;
+ }
+ case Property::MATRIX:
+ {
+ dirty = ( value.Get<Matrix>() != newValue.Get<Matrix>() );
+ break;
+ }
+ case Property::ROTATION:
+ {
+ dirty = ( value.Get<Quaternion>() != newValue.Get<Quaternion>() );
+ break;
+ }
+ case Property::STRING:
+ {
+ dirty = ( value.Get<std::string>() != newValue.Get<std::string>() );
+ break;
+ }
+ case Property::MAP:
+ {
+ dirty = ( !IsPropertyMapIdentical( value.Get<Property::Map>(), newValue.Get<Property::Map>() ) );
+ break;
+ }
+ default:
+ {
+ break;
+ }
+ }
+ }
+ }
+
+ if(dirty)
+ {
+ // Different already, no need any further comparison
+ break;
+ }
+ }
+ }
+
+ return !dirty;
+}
+
void ReportException( v8::Isolate* isolate, v8::TryCatch* tryCatch)
{
v8::HandleScope handleScope( isolate );
return;
}
- for( unsigned int index = 0; index < map.Count() - 1; ++index )
+ for( unsigned int index = 0; index < map.Count(); ++index )
{
const std::string& key = map.GetKey( index );
Property::Value& value = map.GetValue( index );
void GetModuleName( const std::string& fileName, std::string& moduleName );
/**
+ * Compare whether two DALi property maps are identical
+ * @param[in] map1 The first property map to be compared
+ * @param[in] map2 The second property map to be compared
+ * @return true if the two specified property maps are identical or false if not.
+ */
+bool IsPropertyMapIdentical(Property::Map map1, Property::Map map2);
+
+/**
* Report an exception by writing as a warning to the Dali Log
*
* @param[in] try_catch The v8 TryCatch exception object