Home | History | Annotate | Download | only in html
      1 /*
      2  * Copyright (c) 2013, Google Inc. All rights reserved.
      3  *
      4  * Redistribution and use in source and binary forms, with or without
      5  * modification, are permitted provided that the following conditions are
      6  * met:
      7  *
      8  *     * Redistributions of source code must retain the above copyright
      9  * notice, this list of conditions and the following disclaimer.
     10  *     * Redistributions in binary form must reproduce the above
     11  * copyright notice, this list of conditions and the following disclaimer
     12  * in the documentation and/or other materials provided with the
     13  * distribution.
     14  *     * Neither the name of Google Inc. nor the names of its
     15  * contributors may be used to endorse or promote products derived from
     16  * this software without specific prior written permission.
     17  *
     18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     19  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     21  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     22  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     23  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     24  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     28  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     29  */
     30 
     31 #include "config.h"
     32 #include "core/html/TimeRanges.h"
     33 
     34 #include "bindings/core/v8/ExceptionStatePlaceholder.h"
     35 #include <gtest/gtest.h>
     36 
     37 #include <sstream>
     38 
     39 using blink::TimeRanges;
     40 
     41 static std::string ToString(const TimeRanges& ranges)
     42 {
     43     std::stringstream ss;
     44     ss << "{";
     45     for (unsigned i = 0; i < ranges.length(); ++i)
     46         ss << " [" << ranges.start(i, IGNORE_EXCEPTION) << "," << ranges.end(i, IGNORE_EXCEPTION) << ")";
     47     ss << " }";
     48 
     49     return ss.str();
     50 }
     51 
     52 #define ASSERT_RANGE(expected, range) ASSERT_EQ(expected, ToString(*range))
     53 
     54 TEST(TimeRanges, Empty)
     55 {
     56     ASSERT_RANGE("{ }", TimeRanges::create());
     57 }
     58 
     59 TEST(TimeRanges, SingleRange)
     60 {
     61     ASSERT_RANGE("{ [1,2) }", TimeRanges::create(1, 2));
     62 }
     63 
     64 TEST(TimeRanges, CreateFromWebTimeRanges)
     65 {
     66     blink::WebTimeRanges webRanges(static_cast<size_t>(2));
     67     webRanges[0].start = 0;
     68     webRanges[0].end = 1;
     69     webRanges[1].start = 2;
     70     webRanges[1].end = 3;
     71     ASSERT_RANGE("{ [0,1) [2,3) }", TimeRanges::create(webRanges));
     72 }
     73 
     74 TEST(TimeRanges, AddOrder)
     75 {
     76     RefPtrWillBeRawPtr<TimeRanges> rangeA = TimeRanges::create();
     77     RefPtrWillBeRawPtr<TimeRanges> rangeB = TimeRanges::create();
     78 
     79     rangeA->add(0, 2);
     80     rangeA->add(3, 4);
     81     rangeA->add(5, 100);
     82 
     83     std::string expected = "{ [0,2) [3,4) [5,100) }";
     84     ASSERT_RANGE(expected, rangeA);
     85 
     86     // Add the values in rangeA to rangeB in reverse order.
     87     for (int i = rangeA->length() - 1; i >= 0; --i)
     88         rangeB->add(rangeA->start(i, IGNORE_EXCEPTION), rangeA->end(i, IGNORE_EXCEPTION));
     89 
     90     ASSERT_RANGE(expected, rangeB);
     91 }
     92 
     93 TEST(TimeRanges, OverlappingAdds)
     94 {
     95     RefPtrWillBeRawPtr<TimeRanges> ranges = TimeRanges::create();
     96 
     97     ranges->add(0, 2);
     98     ranges->add(10, 11);
     99     ASSERT_RANGE("{ [0,2) [10,11) }", ranges);
    100 
    101     ranges->add(0, 2);
    102     ASSERT_RANGE("{ [0,2) [10,11) }", ranges);
    103 
    104     ranges->add(2, 3);
    105     ASSERT_RANGE("{ [0,3) [10,11) }", ranges);
    106 
    107     ranges->add(2, 6);
    108     ASSERT_RANGE("{ [0,6) [10,11) }", ranges);
    109 
    110     ranges->add(9, 10);
    111     ASSERT_RANGE("{ [0,6) [9,11) }", ranges);
    112 
    113     ranges->add(8, 10);
    114     ASSERT_RANGE("{ [0,6) [8,11) }", ranges);
    115 
    116     ranges->add(-1, 7);
    117     ASSERT_RANGE("{ [-1,7) [8,11) }", ranges);
    118 
    119     ranges->add(6, 9);
    120     ASSERT_RANGE("{ [-1,11) }", ranges);
    121 }
    122 
    123 TEST(TimeRanges, IntersectWith_Self)
    124 {
    125     RefPtrWillBeRawPtr<TimeRanges> ranges = TimeRanges::create(0, 2);
    126 
    127     ASSERT_RANGE("{ [0,2) }", ranges);
    128 
    129     ranges->intersectWith(ranges.get());
    130 
    131     ASSERT_RANGE("{ [0,2) }", ranges);
    132 }
    133 
    134 TEST(TimeRanges, IntersectWith_IdenticalRange)
    135 {
    136     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create(0, 2);
    137     RefPtrWillBeRawPtr<TimeRanges> rangesB = rangesA->copy();
    138 
    139     ASSERT_RANGE("{ [0,2) }", rangesA);
    140     ASSERT_RANGE("{ [0,2) }", rangesB);
    141 
    142     rangesA->intersectWith(rangesB.get());
    143 
    144     ASSERT_RANGE("{ [0,2) }", rangesA);
    145     ASSERT_RANGE("{ [0,2) }", rangesB);
    146 }
    147 
    148 TEST(TimeRanges, IntersectWith_Empty)
    149 {
    150     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create(0, 2);
    151     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    152 
    153     ASSERT_RANGE("{ [0,2) }", rangesA);
    154     ASSERT_RANGE("{ }", rangesB);
    155 
    156     rangesA->intersectWith(rangesB.get());
    157 
    158     ASSERT_RANGE("{ }", rangesA);
    159     ASSERT_RANGE("{ }", rangesB);
    160 }
    161 
    162 TEST(TimeRanges, IntersectWith_DisjointRanges1)
    163 {
    164     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    165     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    166 
    167     rangesA->add(0, 1);
    168     rangesA->add(4, 5);
    169 
    170     rangesB->add(2, 3);
    171     rangesB->add(6, 7);
    172 
    173     ASSERT_RANGE("{ [0,1) [4,5) }", rangesA);
    174     ASSERT_RANGE("{ [2,3) [6,7) }", rangesB);
    175 
    176     rangesA->intersectWith(rangesB.get());
    177 
    178     ASSERT_RANGE("{ }", rangesA);
    179     ASSERT_RANGE("{ [2,3) [6,7) }", rangesB);
    180 }
    181 
    182 TEST(TimeRanges, IntersectWith_DisjointRanges2)
    183 {
    184     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    185     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    186 
    187     rangesA->add(0, 1);
    188     rangesA->add(4, 5);
    189 
    190     rangesB->add(1, 4);
    191     rangesB->add(5, 7);
    192 
    193     ASSERT_RANGE("{ [0,1) [4,5) }", rangesA);
    194     ASSERT_RANGE("{ [1,4) [5,7) }", rangesB);
    195 
    196     rangesA->intersectWith(rangesB.get());
    197 
    198     ASSERT_RANGE("{ }", rangesA);
    199     ASSERT_RANGE("{ [1,4) [5,7) }", rangesB);
    200 }
    201 
    202 TEST(TimeRanges, IntersectWith_CompleteOverlap1)
    203 {
    204     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    205     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    206 
    207     rangesA->add(1, 3);
    208     rangesA->add(4, 5);
    209     rangesA->add(6, 9);
    210 
    211     rangesB->add(0, 10);
    212 
    213     ASSERT_RANGE("{ [1,3) [4,5) [6,9) }", rangesA);
    214     ASSERT_RANGE("{ [0,10) }", rangesB);
    215 
    216     rangesA->intersectWith(rangesB.get());
    217 
    218     ASSERT_RANGE("{ [1,3) [4,5) [6,9) }", rangesA);
    219     ASSERT_RANGE("{ [0,10) }", rangesB);
    220 }
    221 
    222 TEST(TimeRanges, IntersectWith_CompleteOverlap2)
    223 {
    224     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    225     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    226 
    227     rangesA->add(1, 3);
    228     rangesA->add(4, 5);
    229     rangesA->add(6, 9);
    230 
    231     rangesB->add(1, 9);
    232 
    233     ASSERT_RANGE("{ [1,3) [4,5) [6,9) }", rangesA);
    234     ASSERT_RANGE("{ [1,9) }", rangesB);
    235 
    236     rangesA->intersectWith(rangesB.get());
    237 
    238     ASSERT_RANGE("{ [1,3) [4,5) [6,9) }", rangesA);
    239     ASSERT_RANGE("{ [1,9) }", rangesB);
    240 }
    241 
    242 TEST(TimeRanges, IntersectWith_Gaps1)
    243 {
    244     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    245     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    246 
    247     rangesA->add(0, 2);
    248     rangesA->add(4, 6);
    249 
    250     rangesB->add(1, 5);
    251 
    252     ASSERT_RANGE("{ [0,2) [4,6) }", rangesA);
    253     ASSERT_RANGE("{ [1,5) }", rangesB);
    254 
    255     rangesA->intersectWith(rangesB.get());
    256 
    257     ASSERT_RANGE("{ [1,2) [4,5) }", rangesA);
    258     ASSERT_RANGE("{ [1,5) }", rangesB);
    259 }
    260 
    261 TEST(TimeRanges, IntersectWith_Gaps2)
    262 {
    263     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    264     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    265 
    266     rangesA->add(0, 2);
    267     rangesA->add(4, 6);
    268     rangesA->add(8, 10);
    269 
    270     rangesB->add(1, 9);
    271 
    272     ASSERT_RANGE("{ [0,2) [4,6) [8,10) }", rangesA);
    273     ASSERT_RANGE("{ [1,9) }", rangesB);
    274 
    275     rangesA->intersectWith(rangesB.get());
    276 
    277     ASSERT_RANGE("{ [1,2) [4,6) [8,9) }", rangesA);
    278     ASSERT_RANGE("{ [1,9) }", rangesB);
    279 }
    280 
    281 TEST(TimeRanges, IntersectWith_Gaps3)
    282 {
    283     RefPtrWillBeRawPtr<TimeRanges> rangesA = TimeRanges::create();
    284     RefPtrWillBeRawPtr<TimeRanges> rangesB = TimeRanges::create();
    285 
    286     rangesA->add(0, 2);
    287     rangesA->add(4, 7);
    288     rangesA->add(8, 10);
    289 
    290     rangesB->add(1, 5);
    291     rangesB->add(6, 9);
    292 
    293     ASSERT_RANGE("{ [0,2) [4,7) [8,10) }", rangesA);
    294     ASSERT_RANGE("{ [1,5) [6,9) }", rangesB);
    295 
    296     rangesA->intersectWith(rangesB.get());
    297 
    298     ASSERT_RANGE("{ [1,2) [4,5) [6,7) [8,9) }", rangesA);
    299     ASSERT_RANGE("{ [1,5) [6,9) }", rangesB);
    300 }
    301 
    302 TEST(TimeRanges, Nearest)
    303 {
    304     RefPtrWillBeRawPtr<TimeRanges> ranges = TimeRanges::create();
    305     ranges->add(0, 2);
    306     ranges->add(5, 7);
    307 
    308     ASSERT_EQ(0, ranges->nearest(0, 0));
    309     ASSERT_EQ(1, ranges->nearest(1, 0));
    310     ASSERT_EQ(2, ranges->nearest(2, 0));
    311     ASSERT_EQ(2, ranges->nearest(3, 0));
    312     ASSERT_EQ(5, ranges->nearest(4, 0));
    313     ASSERT_EQ(5, ranges->nearest(5, 0));
    314     ASSERT_EQ(7, ranges->nearest(8, 0));
    315 
    316     ranges->add(9, 11);
    317     ASSERT_EQ(7, ranges->nearest(8, 6));
    318     ASSERT_EQ(7, ranges->nearest(8, 8));
    319     ASSERT_EQ(9, ranges->nearest(8, 10));
    320 }
    321