Home | History | Annotate | Download | only in sources
      1 /*
      2  * Copyright (C) 2014 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 /**
     32  * @interface
     33  */
     34 WebInspector.HistoryEntry = function() { }
     35 
     36 WebInspector.HistoryEntry.prototype = {
     37     /**
     38      * @return {boolean}
     39      */
     40     valid: function() { },
     41 
     42     reveal: function() { }
     43 };
     44 
     45 /**
     46  * @constructor
     47  * @param {number} historyDepth
     48  */
     49 WebInspector.SimpleHistoryManager = function(historyDepth)
     50 {
     51     this._entries = [];
     52     this._activeEntryIndex = -1;
     53     this._coalescingReadonly = 0;
     54     this._historyDepth = historyDepth;
     55 }
     56 
     57 WebInspector.SimpleHistoryManager.prototype = {
     58     readOnlyLock: function()
     59     {
     60         ++this._coalescingReadonly;
     61     },
     62 
     63     releaseReadOnlyLock: function()
     64     {
     65         --this._coalescingReadonly;
     66     },
     67 
     68     /**
     69      * @return {boolean}
     70      */
     71     readOnly: function()
     72     {
     73         return !!this._coalescingReadonly;
     74     },
     75 
     76     /**
     77      * @param {!function(!WebInspector.HistoryEntry):boolean} filterOutCallback
     78      */
     79     filterOut: function(filterOutCallback)
     80     {
     81         if (this.readOnly())
     82             return;
     83         var filteredEntries = [];
     84         var removedBeforeActiveEntry = 0;
     85         for (var i = 0; i < this._entries.length; ++i) {
     86             if (!filterOutCallback(this._entries[i])) {
     87                 filteredEntries.push(this._entries[i]);
     88             } else if (i <= this._activeEntryIndex)
     89                 ++removedBeforeActiveEntry;
     90         }
     91         this._entries = filteredEntries;
     92         this._activeEntryIndex = Math.max(0, this._activeEntryIndex - removedBeforeActiveEntry);
     93     },
     94 
     95     /**
     96      * @return {boolean}
     97      */
     98     empty: function()
     99     {
    100         return !this._entries.length;
    101     },
    102 
    103     /**
    104      * @return {?WebInspector.HistoryEntry}
    105      */
    106     active: function()
    107     {
    108         return this.empty() ? null : this._entries[this._activeEntryIndex];
    109     },
    110 
    111     /**
    112      * @param {!WebInspector.HistoryEntry} entry
    113      */
    114     push: function(entry)
    115     {
    116         if (this.readOnly())
    117             return;
    118         if (!this.empty())
    119             this._entries.splice(this._activeEntryIndex + 1);
    120         this._entries.push(entry);
    121         if (this._entries.length > this._historyDepth)
    122             this._entries.shift();
    123         this._activeEntryIndex = this._entries.length - 1;
    124     },
    125 
    126     /**
    127      * @return {boolean}
    128      */
    129     rollback: function()
    130     {
    131         if (this.empty())
    132             return false;
    133 
    134         var revealIndex = this._activeEntryIndex - 1;
    135         while (revealIndex >= 0 && !this._entries[revealIndex].valid())
    136             --revealIndex;
    137         if (revealIndex < 0)
    138             return false;
    139 
    140         this.readOnlyLock();
    141         this._entries[revealIndex].reveal();
    142         this.releaseReadOnlyLock();
    143 
    144         this._activeEntryIndex = revealIndex;
    145         return true;
    146     },
    147 
    148     /**
    149      * @return {boolean}
    150      */
    151     rollover: function()
    152     {
    153         var revealIndex = this._activeEntryIndex + 1;
    154 
    155         while (revealIndex < this._entries.length && !this._entries[revealIndex].valid())
    156             ++revealIndex;
    157         if (revealIndex >= this._entries.length)
    158             return false;
    159 
    160         this.readOnlyLock();
    161         this._entries[revealIndex].reveal();
    162         this.releaseReadOnlyLock();
    163 
    164         this._activeEntryIndex = revealIndex;
    165         return true;
    166     },
    167 };
    168