gnash-commit
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Gnash-commit] gnash ChangeLog server/array.cpp server/array.h


From: Sandro Santilli
Subject: [Gnash-commit] gnash ChangeLog server/array.cpp server/array.h
Date: Thu, 06 Jul 2006 11:38:20 +0000

CVSROOT:        /sources/gnash
Module name:    gnash
Changes by:     Sandro Santilli <strk>  06/07/06 11:38:20

Modified files:
        .              : ChangeLog 
        server         : array.cpp array.h 

Log message:
        * server/array.cpp, server/array.h: implemented Array.sort(flags=0) 
method.

CVSWeb URLs:
http://cvs.savannah.gnu.org/viewcvs/gnash/ChangeLog?cvsroot=gnash&r1=1.472&r2=1.473
http://cvs.savannah.gnu.org/viewcvs/gnash/server/array.cpp?cvsroot=gnash&r1=1.30&r2=1.31
http://cvs.savannah.gnu.org/viewcvs/gnash/server/array.h?cvsroot=gnash&r1=1.11&r2=1.12

Patches:
Index: ChangeLog
===================================================================
RCS file: /sources/gnash/gnash/ChangeLog,v
retrieving revision 1.472
retrieving revision 1.473
diff -u -b -r1.472 -r1.473
--- ChangeLog   6 Jul 2006 08:57:06 -0000       1.472
+++ ChangeLog   6 Jul 2006 11:38:19 -0000       1.473
@@ -1,5 +1,7 @@
 2006-07-06 Sandro Santilli <address@hidden>
 
+       * server/array.cpp, server/array.h: implemented
+       Array.sort(flags=0) method.
        * server/Global.cpp, server/array.cpp, server/array.h:
        had Array unimplemented methods print an ERROR with -v,
        renamed array_init  to array_class_init and change signature

Index: server/array.cpp
===================================================================
RCS file: /sources/gnash/gnash/server/array.cpp,v
retrieving revision 1.30
retrieving revision 1.31
diff -u -b -r1.30 -r1.31
--- server/array.cpp    6 Jul 2006 08:57:06 -0000       1.30
+++ server/array.cpp    6 Jul 2006 11:38:20 -0000       1.31
@@ -61,6 +61,87 @@
 
 static as_object* getArrayInterface();
 
+// Default as_value strict weak comparator (string based)
+struct AsValueLessThen
+{
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               return ( a.to_tu_string() < b.to_tu_string() );
+       }
+};
+
+// Default descending as_value strict weak comparator (string based)
+struct AsValueLessThenDesc
+{
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               return ( a.to_string() > b.to_string() );
+       }
+};
+
+// Case-insensitive as_value strict weak comparator (string)
+struct AsValueLessThenNoCase
+{
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               return ( a.to_tu_stringi() < b.to_tu_stringi() );
+       }
+};
+
+// Descending Case-insensitive as_value strict weak comparator (string)
+struct AsValueLessThenDescNoCase
+{
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               return ( a.to_tu_stringi() > b.to_tu_stringi() );
+       }
+};
+
+// Numeric as_value strict weak comparator 
+struct AsValueLessThenNumeric
+{
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               return ( a.to_number() < b.to_number() );
+       }
+};
+
+// Descending Numeric as_value strict weak comparator 
+struct AsValueLessThenDescNumeric
+{
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               return ( a.to_number() > b.to_number() );
+       }
+};
+
+
+// Custom (ActionScript) comparator 
+struct AsValueFuncComparator
+{
+       as_function& _comp;
+
+       AsValueFuncComparator(as_function& comparator)
+               :
+               _comp(comparator)
+       {
+       }
+
+       bool operator() (const as_value& a, const as_value& b)
+       {
+               // Ugly, but I can't see another way to 
+               // provide fn_call a stack to work on
+               as_environment env;
+               env.push(a);
+               env.push(b);
+
+               as_value ret(false); // bool value
+               fn_call fn(&ret, NULL, &env, 2, 0);
+               _comp(fn);
+               return ( ret.to_bool() );
+       }
+};
+
 // @@ TODO : implement as_array_object's unimplemented functions
 
 as_array_object::as_array_object()
@@ -284,6 +365,92 @@
        as_object::set_member_default(name,val);
 }
 
+std::auto_ptr<as_array_object>
+as_array_object::sorted_indexes(uint8_t flags)
+{
+       assert(flags & as_array_object::fReturnIndexedArray);
+       log_error("Array.sorted_index() method not implemented yet!\n");
+       return std::auto_ptr<as_array_object>(NULL);
+}
+
+void
+as_array_object::sort(uint8_t flags)
+{
+
+       // use sorted_index to use this flag
+       assert( ! (flags & as_array_object::fReturnIndexedArray) );
+
+       bool do_unique = (flags & as_array_object::fUniqueSort);
+
+       // strip the UniqueSort flag, we'll use the do_unique later
+       flags &= ~(as_array_object::fUniqueSort);
+
+       switch ( flags )
+       {
+               case 0: // default sorting
+                       //log_msg("Default sorting");
+                       std::sort(elements.begin(), elements.end(),
+                               AsValueLessThen());
+                       break;
+
+               case as_array_object::fDescending:
+                       //log_msg("Default descending");
+                       std::sort(elements.begin(), elements.end(),
+                               AsValueLessThenDesc());
+                       break;
+
+               case as_array_object::fCaseInsensitive: 
+                       //log_msg("case insensitive");
+                       std::sort(elements.begin(), elements.end(),
+                               AsValueLessThenNoCase());
+                       break;
+
+               case as_array_object::fCaseInsensitive | 
as_array_object::fDescending:
+                       //log_msg("case insensitive descending");
+                       std::sort(elements.begin(), elements.end(),
+                               AsValueLessThenDescNoCase());
+                       break;
+
+               case as_array_object::fNumeric: 
+                       //log_msg("numeric");
+                       std::sort(elements.begin(), elements.end(),
+                               AsValueLessThenNumeric());
+                       break;
+
+               case as_array_object::fNumeric | as_array_object::fDescending:
+                       //log_msg("numeric descending");
+                       std::sort(elements.begin(), elements.end(),
+                               AsValueLessThenDescNumeric());
+                       break;
+
+               default:
+                       log_error("Unhandled sort flags: %d (0x%X)", flags, 
flags);
+                       break;
+       }
+
+       // do the unique step afterwards to simplify code
+       // (altought it's slower, but we can take care of this later)
+       // TODO: use the do_unique variable inside the switch cases
+       // to either use std::sort or std::uniq or similar
+       if ( do_unique )
+       {
+               log_msg("Should unique now");
+       }
+}
+
+void
+as_array_object::sort(as_function& comparator, uint8_t flags)
+{
+
+       // use sorted_index to use this flag
+       assert( ! (flags & as_array_object::fReturnIndexedArray) );
+
+       // Other flags are simply NOT used
+       // (or are them ? the descending one could be!)
+       std::sort(elements.begin(), elements.end(),
+               AsValueFuncComparator(comparator));
+
+}
 
 static void
 array_splice(const fn_call& fn)
@@ -292,15 +459,36 @@
        //as_array_object* array = static_cast<as_array_object*>(fn.this_ptr);
 
        log_error("Array.splice() method not implemented yet!\n");
+       fn.result->set_undefined();
 }
 
 static void
 array_sort(const fn_call& fn)
 {
        assert(dynamic_cast<as_array_object*>(fn.this_ptr));
-       //as_array_object* array = static_cast<as_array_object*>(fn.this_ptr);
+       as_array_object* array = static_cast<as_array_object*>(fn.this_ptr);
+
+       uint8_t flags;
+
+       if ( fn.nargs == 1 && fn.arg(0).get_type() == as_value::NUMBER )
+       {
+               flags=static_cast<uint8_t>(fn.arg(0).to_number());
+       }
+       else if ( fn.nargs == 0 )
+       {
+               flags=0;
+       }
+       else
+       {
+               log_error("Array.sort(comparator) method not implemented!\n");
+               fn.result->set_undefined();
+               return;
+       }
+
+       array->sort(flags);
+       fn.result->set_undefined(); // returns void
+       return;
 
-       log_error("Array.sort() method not implemented yet!\n");
 }
 
 static void
@@ -310,6 +498,7 @@
        //as_array_object* array = static_cast<as_array_object*>(fn.this_ptr);
 
        log_error("Array.sortOn() method not implemented yet!\n");
+       fn.result->set_undefined();
 }
 
 // Callback to report array length
@@ -605,11 +794,11 @@
        proto->set_member("sortOn", &array_sortOn);
        proto->set_member("reverse", &array_reverse);
        proto->set_member("toString", &array_to_string);
-       proto->set_member("CASEINSENSITIVE", 1);
-       proto->set_member("DESCENDING", 2);
-       proto->set_member("UNIQUESORT", 4);
-       proto->set_member("RETURNINDEXEDARRAY", 8);
-       proto->set_member("NUMERIC", 16);
+       proto->set_member("CASEINSENSITIVE", as_array_object::fCaseInsensitive);
+       proto->set_member("DESCENDING", as_array_object::fDescending);
+       proto->set_member("UNIQUESORT", as_array_object::fUniqueSort);
+       proto->set_member("RETURNINDEXEDARRAY", 
as_array_object::fReturnIndexedArray);
+       proto->set_member("NUMERIC", as_array_object::fNumeric);
 }
 
 static as_object*

Index: server/array.h
===================================================================
RCS file: /sources/gnash/gnash/server/array.h,v
retrieving revision 1.11
retrieving revision 1.12
diff -u -b -r1.11 -r1.12
--- server/array.h      6 Jul 2006 08:57:06 -0000       1.11
+++ server/array.h      6 Jul 2006 11:38:20 -0000       1.12
@@ -57,8 +57,30 @@
 /// The Array ActionScript object
 class as_array_object : public as_object
 {
+
 public:
 
+       /// Sort flags
+       enum SortFlags {
+
+               /// Case-insensitive (z precedes A)
+               fCaseInsensitive        = (1<<0), // 1
+
+               /// Descending order (b precedes a)
+               fDescending             = (1<<1), // 2
+
+               /// Remove consecutive equal elements
+               fUniqueSort             = (1<<2), // 4
+
+               /// Don't modify the array, rather return
+               /// a new array containing indexes into it
+               /// in sorted order.
+               fReturnIndexedArray     = (1<<3), // 8
+
+               /// Numerical sort (9 preceeds 10)
+               fNumeric                = (1<<4) // 16
+       };
+
        as_array_object();
 
        as_array_object(const as_array_object& other);
@@ -88,6 +110,18 @@
        std::auto_ptr<as_array_object> slice(
                unsigned int start, unsigned int one_past_end);
 
+       /// Sort the array, using given values comparator
+       void sort(as_function& comparator, uint8_t flags=0);
+
+       void sort(uint8_t flags=0);
+
+       /// Return a new array containing sorted index of this array
+       //
+       /// NOTE: assert(flags & Array::fReturnIndexedArray)
+       std::auto_ptr<as_array_object> sorted_indexes(uint8_t flags);
+
+       std::auto_ptr<as_array_object> sorted_indexes(as_function& comparator, 
uint8_t flags);
+
        /// Overridden to provide 'length' member
        virtual bool get_member(const tu_stringi& name, as_value* val);
 




reply via email to

[Prev in Thread] Current Thread [Next in Thread]