Skip to content

Commit ba85275

Browse files
Pauanalexcrichton
authored andcommitted
Adding in more methods for Array (#1749)
1 parent 4e19ead commit ba85275

File tree

2 files changed

+151
-1
lines changed

2 files changed

+151
-1
lines changed

crates/js-sys/src/lib.rs

+34-1
Original file line numberDiff line numberDiff line change
@@ -130,10 +130,30 @@ extern "C" {
130130
#[derive(Clone, Debug, PartialEq, Eq)]
131131
pub type Array;
132132

133-
/// Creates a new empty array
133+
/// Creates a new empty array.
134134
#[wasm_bindgen(constructor)]
135135
pub fn new() -> Array;
136136

137+
/// Creates a new array with the specified length (elements are initialized to `undefined`).
138+
#[wasm_bindgen(constructor)]
139+
pub fn new_with_length(len: u32) -> Array;
140+
141+
/// Retrieves the element at the index (returns `undefined` if the index is out of range).
142+
#[wasm_bindgen(method, structural, indexing_getter)]
143+
pub fn get(this: &Array, index: u32) -> JsValue;
144+
145+
/// Sets the element at the index (auto-enlarges the array if the index is out of range).
146+
#[wasm_bindgen(method, structural, indexing_setter)]
147+
pub fn set(this: &Array, index: u32, value: JsValue);
148+
149+
/// Deletes the element at the index (does nothing if the index is out of range).
150+
///
151+
/// The element at the index is set to `undefined`.
152+
///
153+
/// This does not resize the array, the array will still be the same length.
154+
#[wasm_bindgen(method, structural, indexing_deleter)]
155+
pub fn delete(this: &Array, index: u32);
156+
137157
/// The `Array.from()` method creates a new, shallow-copied `Array` instance
138158
/// from an array-like or iterable object.
139159
#[wasm_bindgen(static_method_of = Array)]
@@ -405,6 +425,19 @@ extern "C" {
405425
pub fn unshift(this: &Array, value: &JsValue) -> u32;
406426
}
407427

428+
// TODO pre-initialize the Array with the correct length using TrustedLen
429+
impl<A> std::iter::FromIterator<A> for Array where A: AsRef<JsValue> {
430+
fn from_iter<T>(iter: T) -> Array where T: IntoIterator<Item = A> {
431+
let out = Array::new();
432+
433+
for value in iter {
434+
out.push(value.as_ref());
435+
}
436+
437+
out
438+
}
439+
}
440+
408441
// ArrayBuffer
409442
#[wasm_bindgen]
410443
extern "C" {

crates/js-sys/tests/wasm/Array.rs

+117
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
use js_sys::*;
2+
use std::iter::FromIterator;
23
use wasm_bindgen::JsCast;
34
use wasm_bindgen::JsValue;
45
use wasm_bindgen_test::*;
@@ -25,6 +26,122 @@ fn to_rust(arr: &Array) -> Vec<JsValue> {
2526
result
2627
}
2728

29+
#[wasm_bindgen_test]
30+
fn from_iter() {
31+
assert_eq!(
32+
to_rust(&vec![
33+
JsValue::from("a"),
34+
JsValue::from("b"),
35+
JsValue::from("c"),
36+
].into_iter().collect()),
37+
vec!["a", "b", "c"],
38+
);
39+
40+
assert_eq!(
41+
to_rust(&vec![
42+
JsValue::from("a"),
43+
JsValue::from("b"),
44+
JsValue::from("c"),
45+
].iter().collect()),
46+
vec!["a", "b", "c"],
47+
);
48+
49+
let array = js_array![1u32, 2u32, 3u32];
50+
51+
assert_eq!(
52+
to_rust(&vec![
53+
array.clone(),
54+
].into_iter().collect()),
55+
vec![JsValue::from(array.clone())],
56+
);
57+
58+
assert_eq!(
59+
to_rust(&vec![
60+
array.clone(),
61+
].iter().collect()),
62+
vec![JsValue::from(array)],
63+
);
64+
65+
assert_eq!(
66+
to_rust(&vec![
67+
5,
68+
10,
69+
20,
70+
].into_iter().map(JsValue::from).collect()),
71+
vec![5, 10, 20],
72+
);
73+
74+
assert_eq!(
75+
to_rust(&Array::from_iter(&[
76+
JsValue::from("a"),
77+
JsValue::from("b"),
78+
JsValue::from("c"),
79+
])),
80+
vec!["a", "b", "c"],
81+
);
82+
83+
let v = vec![
84+
"a",
85+
"b",
86+
"c",
87+
];
88+
89+
assert_eq!(
90+
to_rust(&Array::from_iter(v.into_iter().map(|s| JsValue::from(s)))),
91+
vec!["a", "b", "c"],
92+
);
93+
}
94+
95+
#[wasm_bindgen_test]
96+
fn new_with_length() {
97+
let array = Array::new_with_length(5);
98+
assert_eq!(array.length(), 5);
99+
assert_eq!(array.get(4), JsValue::undefined());
100+
array.set(4, JsValue::from("a"));
101+
assert_eq!(array.get(4), "a");
102+
assert_eq!(array.length(), 5);
103+
}
104+
105+
#[wasm_bindgen_test]
106+
fn get() {
107+
let array = js_array!["a", "c", "x", "n"];
108+
assert_eq!(array.length(), 4);
109+
assert_eq!(array.get(0), "a");
110+
assert_eq!(array.get(3), "n");
111+
assert_eq!(array.get(4), JsValue::undefined());
112+
}
113+
114+
#[wasm_bindgen_test]
115+
fn set() {
116+
let array = js_array!["a", "c", "x", "n"];
117+
assert_eq!(array.length(), 4);
118+
assert_eq!(array.get(0), "a");
119+
array.set(0, JsValue::from("b"));
120+
assert_eq!(array.get(0), "b");
121+
122+
assert_eq!(array.get(4), JsValue::undefined());
123+
assert_eq!(array.length(), 4);
124+
array.set(4, JsValue::from("d"));
125+
assert_eq!(array.length(), 5);
126+
assert_eq!(array.get(4), "d");
127+
128+
assert_eq!(array.get(10), JsValue::undefined());
129+
assert_eq!(array.length(), 5);
130+
array.set(10, JsValue::from("z"));
131+
assert_eq!(array.length(), 11);
132+
assert_eq!(array.get(10), "z");
133+
assert_eq!(array.get(9), JsValue::undefined());
134+
}
135+
136+
#[wasm_bindgen_test]
137+
fn delete() {
138+
let array = js_array!["a", "c", "x", "n"];
139+
assert_eq!(array.length(), 4);
140+
assert_eq!(array.get(0), "a");
141+
array.delete(0);
142+
assert_eq!(array.get(0), JsValue::undefined());
143+
}
144+
28145
#[wasm_bindgen_test]
29146
fn filter() {
30147
let array = js_array!["a", "c", "x", "n"];

0 commit comments

Comments
 (0)