Skip to content

Commit

Permalink
Implement PartialEq for VTag
Browse files Browse the repository at this point in the history
  • Loading branch information
Penny Wing committed Jan 1, 2018
1 parent 874d84b commit aa28678
Show file tree
Hide file tree
Showing 5 changed files with 243 additions and 2 deletions.
4 changes: 2 additions & 2 deletions src/macros.rs
Original file line number Diff line number Diff line change
Expand Up @@ -127,9 +127,9 @@ pub fn unpack<MSG>(mut stack: Stack<MSG>) -> VTag<MSG> {
}

#[doc(hidden)]
pub fn set_value<MSG, T: ToString>(stack: &mut Stack<MSG>, value: &T) {
pub fn set_value<MSG, T: ToString>(stack: &mut Stack<MSG>, value: T) {
if let Some(node) = stack.last_mut() {
node.set_value(value);
node.set_value(&value);
} else {
panic!("no tag to set value: {}", value.to_string());
}
Expand Down
24 changes: 24 additions & 0 deletions src/virtual_dom/vnode.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
//! This module contains the implementation of abstract virtual node.
use std::fmt;
use std::cmp::PartialEq;
use stdweb::web::{INode, Node, Element, TextNode, document};
use virtual_dom::{VTag, VText, Messages};

Expand Down Expand Up @@ -177,3 +178,26 @@ impl<MSG> fmt::Debug for VNode<MSG> {
}
}
}

impl<MSG> PartialEq for VNode<MSG> {
fn eq(&self, other: &VNode<MSG>) -> bool {
match *self {
VNode::VTag { vtag: ref vtag_a, .. } => {
match *other {
VNode::VTag { vtag: ref vtag_b, .. } => {
vtag_a == vtag_b
},
_ => false
}
},
VNode::VText { vtext: ref vtext_a, .. } => {
match *other {
VNode::VText { vtext: ref vtext_b, .. } => {
vtext_a == vtext_b
},
_ => false
}
}
}
}
}
57 changes: 57 additions & 0 deletions src/virtual_dom/vtag.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
use std::fmt;
use std::borrow::Cow;
use std::collections::HashSet;
use std::cmp::PartialEq;
use stdweb::web::{IElement, Element, EventListenerHandle};
use stdweb::web::html_element::InputElement;
use stdweb::unstable::TryFrom;
Expand Down Expand Up @@ -304,3 +305,59 @@ fn remove_attribute(element: &Element, name: &str) {
fn set_checked(input: &InputElement, value: bool) {
js!( @{input}.checked = @{value}; );
}

impl<MSG> PartialEq for VTag<MSG> {
fn eq(&self, other: &VTag<MSG>) -> bool {
if self.tag != other.tag {
return false;
}

if self.value != other.value {
return false;
}

if self.kind != other.kind {
return false;
}

if self.checked != other.checked {
return false;
}

if self.listeners.len() != other.listeners.len() {
return false;
}

for i in 0..self.listeners.len() {
let a = &self.listeners[i];
let b = &other.listeners[i];

if a.kind() != b.kind() {
return false;
}
}

if self.attributes != other.attributes {
return false;
}

if self.classes != other.classes {
return false;
}

if self.childs.len() != other.childs.len() {
return false;
}

for i in 0..self.childs.len() {
let a = &self.childs[i];
let b = &other.childs[i];

if a != b {
return false;
}
}

true
}
}
6 changes: 6 additions & 0 deletions src/virtual_dom/vtext.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
//! This module contains the implementation of a virtual text node `VText`.
use std::fmt;
use std::cmp::PartialEq;
use stdweb::web::{INode, TextNode};

/// A type for a virtual
Expand Down Expand Up @@ -36,3 +37,8 @@ impl fmt::Debug for VText {
}
}

impl PartialEq for VText {
fn eq(&self, other: &VText) -> bool {
return self.text == other.text;
}
}
154 changes: 154 additions & 0 deletions tests/vtag_test.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,154 @@
#[macro_use]
extern crate yew;

use yew::virtual_dom::VTag;

#[test]
fn it_compares_tags() {
let a: VTag<()> = html! {
<div></div>
};

let b: VTag<()> = html! {
<div></div>
};

let c: VTag<()> = html! {
<p></p>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_text() {
let a: VTag<()> = html! {
<div>{ "correct" }</div>
};

let b: VTag<()> = html! {
<div>{ "correct" }</div>
};

let c: VTag<()> = html! {
<div>{ "incorrect" }</div>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_attributes() {
let a: VTag<()> = html! {
<div a="test",></div>
};

let b: VTag<()> = html! {
<div a="test",></div>
};

let c: VTag<()> = html! {
<div a="fail",></div>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_children() {
let a: VTag<()> = html! {
<div>
<p></p>
</div>
};

let b: VTag<()> = html! {
<div>
<p></p>
</div>
};

let c: VTag<()> = html! {
<div>
<span></span>
</div>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_classes() {
let a: VTag<()> = html! {
<div class="test",></div>
};

let b: VTag<()> = html! {
<div class="test",></div>
};

let c: VTag<()> = html! {
<div class="fail",></div>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_values() {
let a: VTag<()> = html! {
<input value="test",/>
};

let b: VTag<()> = html! {
<input value="test",/>
};

let c: VTag<()> = html! {
<input value="fail",/>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_kinds() {
let a: VTag<()> = html! {
<input type="text",/>
};

let b: VTag<()> = html! {
<input type="text",/>
};

let c: VTag<()> = html! {
<input type="hidden",/>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

#[test]
fn it_compares_checked() {
let a: VTag<()> = html! {
<input type="checkbox", checked=false,/>
};

let b: VTag<()> = html! {
<input type="checkbox", checked=false,/>
};

let c: VTag<()> = html! {
<input type="checkbox", checked=true,/>
};

assert_eq!(a, b);
assert_ne!(a, c);
}

0 comments on commit aa28678

Please sign in to comment.