Browse Source

incremental work on Array.prototype

Sebastien Ros 12 years ago
parent
commit
9c648a6933

+ 1 - 1
Jint/Native/Array/ArrayInstance.cs

@@ -4,7 +4,7 @@ using Jint.Runtime.Descriptors;
 
 
 namespace Jint.Native.Array
 namespace Jint.Native.Array
 {
 {
-    public sealed class ArrayInstance : ObjectInstance
+    public class ArrayInstance : ObjectInstance
     {
     {
         private readonly Engine _engine;
         private readonly Engine _engine;
  
  

+ 69 - 6
Jint/Native/Array/ArrayPrototype.cs

@@ -8,7 +8,7 @@ namespace Jint.Native.Array
     /// <summary>
     /// <summary>
     ///     http://www.ecma-international.org/ecma-262/5.1/#sec-15.4.4
     ///     http://www.ecma-international.org/ecma-262/5.1/#sec-15.4.4
     /// </summary>
     /// </summary>
-    public sealed class ArrayPrototype : ObjectInstance
+    public sealed class ArrayPrototype : ArrayInstance
     {
     {
         private ArrayPrototype(Engine engine) : base(engine)
         private ArrayPrototype(Engine engine) : base(engine)
         {
         {
@@ -16,8 +16,13 @@ namespace Jint.Native.Array
 
 
         public static ArrayPrototype CreatePrototypeObject(Engine engine, ArrayConstructor arrayConstructor)
         public static ArrayPrototype CreatePrototypeObject(Engine engine, ArrayConstructor arrayConstructor)
         {
         {
-            var obj = new ArrayPrototype(engine) {Extensible = true};
+            var obj = new ArrayPrototype(engine)
+                {
+                    Extensible = true, 
+                    Prototype = engine.Object.PrototypeObject
+                };
 
 
+            obj.FastAddProperty("length", 0, false, false, false);
             obj.FastAddProperty("constructor", arrayConstructor, false, false, false);
             obj.FastAddProperty("constructor", arrayConstructor, false, false, false);
 
 
             return obj;
             return obj;
@@ -25,7 +30,7 @@ namespace Jint.Native.Array
 
 
         public void Configure()
         public void Configure()
         {
         {
-            FastAddProperty("toString", new ClrFunctionInstance<object, object>(Engine, ToArrayString), false, false, false);
+            FastAddProperty("toString", new ClrFunctionInstance<object, object>(Engine, ToString), false, false, false);
             FastAddProperty("toLocaleString", new ClrFunctionInstance<object, object>(Engine, ToLocaleString), false, false, false);
             FastAddProperty("toLocaleString", new ClrFunctionInstance<object, object>(Engine, ToLocaleString), false, false, false);
             FastAddProperty("concat", new ClrFunctionInstance<object, object>(Engine, Concat), false, false, false);
             FastAddProperty("concat", new ClrFunctionInstance<object, object>(Engine, Concat), false, false, false);
             FastAddProperty("join", new ClrFunctionInstance<object, object>(Engine, Join), false, false, false);
             FastAddProperty("join", new ClrFunctionInstance<object, object>(Engine, Join), false, false, false);
@@ -125,7 +130,53 @@ namespace Jint.Native.Array
 
 
         private object ToLocaleString(object thisObj, object[] arguments)
         private object ToLocaleString(object thisObj, object[] arguments)
         {
         {
-            throw new NotImplementedException();
+            var array = TypeConverter.ToObject(Engine, thisObj);
+            var arrayLen = array.Get("length");
+            var len = TypeConverter.ToUint32(arrayLen);
+            var separator = ",";
+            if (len == 0)
+            {
+                return "";
+            }
+            object r;
+            var firstElement = array.Get("0");
+            if (firstElement == Null.Instance || firstElement == Undefined.Instance)
+            {
+                r = "";
+            }
+            else
+            {
+                var elementObj = TypeConverter.ToObject(Engine, firstElement);
+                var func = elementObj.Get("toLocaleString") as ICallable;
+                if (func == null)
+                {
+                    throw new JavaScriptException(Engine.TypeError);
+                }
+                r = func.Call(elementObj, Arguments.Empty);
+            }
+            for (var k = 1; k < len; k++)
+            {
+                string s = r + separator;
+                var nextElement = array.Get(k.ToString());
+                if (nextElement == Undefined.Instance || nextElement == Null.Instance)
+                {
+                    r = "";
+                }
+                else
+                {
+                    var elementObj = TypeConverter.ToObject(Engine, firstElement);
+                    var func = elementObj.Get("toLocaleString") as ICallable;
+                    if (func == null)
+                    {
+                        throw new JavaScriptException(Engine.TypeError);
+                    }
+                    r = func.Call(elementObj, Arguments.Empty);
+                }
+                r = s + r;
+            }
+
+            return r;
+
         }
         }
 
 
         private object Concat(object thisObj, object[] arguments)
         private object Concat(object thisObj, object[] arguments)
@@ -133,9 +184,21 @@ namespace Jint.Native.Array
             throw new NotImplementedException();
             throw new NotImplementedException();
         }
         }
 
 
-        private object ToArrayString(object thisObj, object[] arguments)
+        private object ToString(object thisObj, object[] arguments)
         {
         {
-            throw new NotImplementedException();
+            var array = TypeConverter.ToObject(Engine, thisObj);
+            var func = array.Get("join") as ICallable;
+            if (func == null)
+            {
+                func = Engine.Object.PrototypeObject.Get("toString") as ICallable;
+                
+                if (func == null)
+                {
+                    throw new ArgumentException();
+                }
+            }
+
+            return func.Call(array, Arguments.Empty);
         }
         }
 
 
         private object ReduceRight(ArrayInstance arg1, object[] arg2)
         private object ReduceRight(ArrayInstance arg1, object[] arg2)

+ 11 - 4
Jint/Native/Function/FunctionPrototype.cs

@@ -1,5 +1,6 @@
 using System;
 using System;
 using System.Collections.Generic;
 using System.Collections.Generic;
+using System.Linq;
 using Jint.Native.Object;
 using Jint.Native.Object;
 using Jint.Runtime;
 using Jint.Runtime;
 using Jint.Runtime.Interop;
 using Jint.Runtime.Interop;
@@ -30,9 +31,9 @@ namespace Jint.Native.Function
         public void Configure()
         public void Configure()
         {
         {
             FastAddProperty("constructor", Engine.Function, false, false, false);
             FastAddProperty("constructor", Engine.Function, false, false, false);
-            FastAddProperty("toString", new ClrFunctionInstance<object, object>(Engine, ToFunctionString), false, false, false);
+            FastAddProperty("toString", new ClrFunctionInstance<object, object>(Engine, ToString), false, false, false);
             FastAddProperty("apply", new ClrFunctionInstance<object, object>(Engine, Apply), false, false, false);
             FastAddProperty("apply", new ClrFunctionInstance<object, object>(Engine, Apply), false, false, false);
-            FastAddProperty("call", new ClrFunctionInstance<object, object>(Engine, Call), false, false, false);
+            FastAddProperty("call", new ClrFunctionInstance<object, object>(Engine, Call, 1), false, false, false);
             FastAddProperty("bind", new ClrFunctionInstance<object, object>(Engine, Bind), false, false, false);
             FastAddProperty("bind", new ClrFunctionInstance<object, object>(Engine, Bind), false, false, false);
         }
         }
 
 
@@ -41,7 +42,7 @@ namespace Jint.Native.Function
             throw new NotImplementedException();
             throw new NotImplementedException();
         }
         }
 
 
-        private object ToFunctionString(object thisObj, object[] arguments)
+        private object ToString(object thisObj, object[] arguments)
         {
         {
             throw new NotImplementedException();
             throw new NotImplementedException();
         }
         }
@@ -87,7 +88,13 @@ namespace Jint.Native.Function
 
 
         public override object Call(object thisObject, object[] arguments)
         public override object Call(object thisObject, object[] arguments)
         {
         {
-            return Undefined.Instance;
+            var func = thisObject as ICallable;
+            if (func == null)
+            {
+                return new JavaScriptException(Engine.TypeError);
+            }
+
+            return func.Call(arguments[0], arguments.Skip(1).ToArray());
         }
         }
     }
     }
 }
 }

+ 35 - 5
Jint/Native/Object/ObjectPrototype.cs

@@ -23,27 +23,57 @@ namespace Jint.Native.Object
         public void Configure()
         public void Configure()
         {
         {
             FastAddProperty("toString", new ClrFunctionInstance<object, string>(Engine, ToString), false, false, false);
             FastAddProperty("toString", new ClrFunctionInstance<object, string>(Engine, ToString), false, false, false);
-            FastAddProperty("toLocaleString", new ClrFunctionInstance<object, string>(Engine, ToLocaleString), false, false, false);
+            FastAddProperty("toLocaleString", new ClrFunctionInstance<object, object>(Engine, ToLocaleString), false, false, false);
             FastAddProperty("valueOf", new ClrFunctionInstance<object, object>(Engine, ValueOf), false, false, false);
             FastAddProperty("valueOf", new ClrFunctionInstance<object, object>(Engine, ValueOf), false, false, false);
             FastAddProperty("hasOwnProperty", new ClrFunctionInstance<object, bool>(Engine, HasOwnProperty), false, false, false);
             FastAddProperty("hasOwnProperty", new ClrFunctionInstance<object, bool>(Engine, HasOwnProperty), false, false, false);
             FastAddProperty("isPrototypeOf", new ClrFunctionInstance<object, bool>(Engine, IsPrototypeOf), false, false, false);
             FastAddProperty("isPrototypeOf", new ClrFunctionInstance<object, bool>(Engine, IsPrototypeOf), false, false, false);
             FastAddProperty("propertyIsEnumerable", new ClrFunctionInstance<object, bool>(Engine, PropertyIsEnumerable), false, false, false);
             FastAddProperty("propertyIsEnumerable", new ClrFunctionInstance<object, bool>(Engine, PropertyIsEnumerable), false, false, false);
         }
         }
+
         private bool PropertyIsEnumerable(object thisObject, object[] arguments)
         private bool PropertyIsEnumerable(object thisObject, object[] arguments)
         {
         {
             throw new NotImplementedException();
             throw new NotImplementedException();
         }
         }
+
         private object ValueOf(object thisObject, object[] arguments)
         private object ValueOf(object thisObject, object[] arguments)
         {
         {
-            throw new NotImplementedException();
+            var o = TypeConverter.ToObject(Engine, thisObject);
+            return o;
         }
         }
+
         private bool IsPrototypeOf(object thisObject, object[] arguments)
         private bool IsPrototypeOf(object thisObject, object[] arguments)
         {
         {
-            throw new NotImplementedException();
+            var v = arguments[0] as ObjectInstance;
+            if (v == null)
+            {
+                return false;
+            }
+
+            var o = TypeConverter.ToObject(Engine, thisObject);
+            while (true)
+            {
+                v = v.Prototype;
+                if (v == null)
+                {
+                    return false;
+                }
+                if (o == v)
+                {
+                    return true;
+                }
+
+            }
         }
         }
-        private string ToLocaleString(object thisObject, object[] arguments)
+
+        private object ToLocaleString(object thisObject, object[] arguments)
         {
         {
-            throw new NotImplementedException();
+            var o = TypeConverter.ToObject(Engine, thisObject);
+            var toString = o.Get("toString") as ICallable;
+            if (toString == null)
+            {
+                throw new JavaScriptException(Engine.TypeError);
+            }
+            return toString.Call(o, Arguments.Empty);
         }
         }
 
 
         /// <summary>
         /// <summary>

+ 6 - 0
Jint/Runtime/Interop/ClrFunctionInstance.cs

@@ -17,6 +17,12 @@ namespace Jint.Runtime.Interop
             Prototype = engine.Function.PrototypeObject;
             Prototype = engine.Function.PrototypeObject;
         }
         }
 
 
+        public ClrFunctionInstance(Engine engine, Func<TObject, object[], TResult> func, int length)
+            : this(engine, func)
+        {
+            FastAddProperty("length", length, false, false, false);
+        }
+
         public override object Call(object thisObject, object[] arguments)
         public override object Call(object thisObject, object[] arguments)
         {
         {
             var result = _func((TObject) thisObject, arguments);
             var result = _func((TObject) thisObject, arguments);