import 'dart:html';
import 'dart:html_common';

import 'package:expect/minitest.dart';

main() {
  var t1 = new Text('T1'),
      t2 = new Text('T2'),
      t3 = new Text('T3'),
      t4 = new Text('T4');

  var d1 = new DivElement(),
      d2 = new DivElement(),
      d3 = new DivElement();

  createTestDiv() {
    var testDiv = new DivElement();
    testDiv
      ..append(t1)
      ..append(d1)
      ..append(t2)
      ..append(d2)
      ..append(t3)
      ..append(d3)
      ..append(t4);
    return testDiv;
  }

  test('FilteredElementList.insert test', () {
    var i = new DivElement();

    // Insert before first element
    var nodeList = createTestDiv();
    var elementList = new FilteredElementList(nodeList);
    elementList.insert(0, i);
    expect(nodeList.childNodes[0], t1);
    expect(nodeList.childNodes[1], i);
    expect(nodeList.childNodes[2], d1);

    // Insert in middle
    nodeList = createTestDiv();
    elementList = new FilteredElementList(nodeList);
    elementList.insert(1, i);
    expect(nodeList.childNodes[2], t2);
    expect(nodeList.childNodes[3], i);
    expect(nodeList.childNodes[4], d2);

    // Insert before last element
    nodeList = createTestDiv();
    elementList = new FilteredElementList(nodeList);
    elementList.insert(2, i);
    expect(nodeList.childNodes[4], t3);
    expect(nodeList.childNodes[5], i);
    expect(nodeList.childNodes[6], d3);
  });

  test('FilteredElementList.insertAll test', () {
    var i1 = new DivElement(),
        i2 = new DivElement();

    var it = [i1, i2];

    // Insert before first element
    var nodeList = createTestDiv();
    var elementList = new FilteredElementList(nodeList);
    elementList.insertAll(0, it);
    expect(nodeList.childNodes[0], t1);
    expect(nodeList.childNodes[1], i1);
    expect(nodeList.childNodes[2], i2);
    expect(nodeList.childNodes[3], d1);

    // Insert in middle
    nodeList = createTestDiv();
    elementList = new FilteredElementList(nodeList);
    elementList.insertAll(1, it);
    expect(nodeList.childNodes[2], t2);
    expect(nodeList.childNodes[3], i1);
    expect(nodeList.childNodes[4], i2);
    expect(nodeList.childNodes[5], d2);

    // Insert before last element
    nodeList = createTestDiv();
    elementList = new FilteredElementList(nodeList);
    elementList.insertAll(2, it);
    expect(nodeList.childNodes[4], t3);
    expect(nodeList.childNodes[5], i1);
    expect(nodeList.childNodes[6], i2);
    expect(nodeList.childNodes[7], d3);
  });

 test('FilteredElementList.insertAndRemove', () {
    var emptyDiv = new DivElement();
    var elementList = new FilteredElementList(emptyDiv);
    expect(() => elementList[0], throwsRangeError);
    expect(() => elementList.insert(2, new BRElement()), throwsRangeError);
    var br = new BRElement();
    elementList.insert(0, br);
    expect(elementList.removeLast(), br);
    elementList.add(br);
    expect(elementList.remove(br), isTrue);
    var br2 = new BRElement();
    elementList.add(br);
    expect(elementList.remove(br2), isFalse);
    expect(elementList[0], br);
    expect(() => elementList[1], throwsRangeError);
 });
}
