<!DOCTYPE html>
<!--
Copyright (c) 2015 The Chromium Authors. All rights reserved.
Use of this source code is governed by a BSD-style license that can be
found in the LICENSE file.
-->

<link rel="import" href="/model/event_set.html">
<link rel="import" href="/ui/analysis/analysis_link.html">
<link rel="import" href="/ui/analysis/flow_classifier.html">
<link rel="import" href="/ui/base/dom_helpers.html">
<link rel="import" href="/ui/base/table.html">

<polymer-element name="tr-ui-a-related-events">
  <template>
    <style>
    :host {
      display: flex;
      flex-direction: column;
    }
    #table {
      flex: 1 1 auto;
      align-self: stretch;
    }
    </style>
    <tr-ui-b-table id="table"></tr-ui-b-table>
  </template>

  <script>
  'use strict';

  Polymer({
    ready: function() {
      this.eventGroups_ = [];

      this.$.table.tableColumns = [
        {
          title: 'Event(s)',
          value: function(row) {
            var typeEl = document.createElement('span');
            typeEl.innerText = row.type;
            if (row.tooltip)
              typeEl.title = row.tooltip;
            return typeEl;
          },
          width: '150px'
        },
        {
          title: 'Link',
          width: '100%',
          value: function(row) {
            var linkEl = document.createElement('tr-ui-a-analysis-link');
            if (row.name)
              linkEl.setSelectionAndContent(row.selection, row.name);
            else
              linkEl.selection = row.selection;
            return linkEl;
          }
        }
      ];
    },

    hasRelatedEvents: function() {
      return (this.eventGroups_ && this.eventGroups_.length > 0);
    },

    setRelatedEvents: function(eventSet) {
      this.eventGroups_ = [];
      this.addConnectedFlows_(eventSet);
      this.addConnectedEvents_(eventSet);
      this.addOverlappingSamples_(eventSet);
      this.updateContents_();
    },

    addConnectedFlows_: function(eventSet) {
      var classifier = new tr.ui.analysis.FlowClassifier();
      eventSet.forEach(function(slice) {
        if (slice.inFlowEvents) {
          slice.inFlowEvents.forEach(function(flow) {
            classifier.addInFlow(flow);
          });
        }
        if (slice.outFlowEvents) {
          slice.outFlowEvents.forEach(function(flow) {
            classifier.addOutFlow(flow);
          });
        }
      });
      if (!classifier.hasEvents())
        return;

      var addToEventGroups = function(type, flowEvent) {
        this.eventGroups_.push({
          type: type,
          selection: new tr.model.EventSet(flowEvent),
          name: flowEvent.title
        });
      };

      classifier.inFlowEvents.forEach(
          addToEventGroups.bind(this, 'Incoming flow'));
      classifier.outFlowEvents.forEach(
          addToEventGroups.bind(this, 'Outgoing flow'));
      classifier.internalFlowEvents.forEach(
          addToEventGroups.bind(this, 'Internal flow'));
    },

    addConnectedEvents_: function(eventSet) {
      if (eventSet.length === 0)
        return;

      var precedingEvents = new tr.model.EventSet(eventSet.toArray());
      var followingEvents = new tr.model.EventSet(eventSet.toArray());

      var i = 0;
      while (i < precedingEvents.length) {
        var event = precedingEvents[i];
        this.addInFlowEvents_(event, precedingEvents);
        this.addAncestors_(event, precedingEvents);
        if (event.startSlice)
          precedingEvents.push(event.startSlice);
        i++;
      }

      i = 0;
      while (i < followingEvents.length) {
        var event = followingEvents[i];
        this.addOutFlowEvents_(event, followingEvents);
        this.addDescendents_(event, followingEvents);
        if (event.endSlice)
          followingEvents.push(event.endSlice);
        i++;
      }

      var allEvents = new tr.model.EventSet(precedingEvents.toArray());
      followingEvents.forEach(function(e) {
        allEvents.push(e);
      });
      i = 0;
      while (i < allEvents.length) {
        var event = allEvents[i];
        this.addInFlowEvents_(event, allEvents);
        this.addOutFlowEvents_(event, allEvents);
        this.addAncestors_(event, allEvents);
        this.addDescendents_(event, allEvents);
        if (event.startSlice)
          allEvents.push(event.startSlice);
        if (event.endSlice)
          allEvents.push(event.endSlice);
        i++;
      }

      if (precedingEvents.length !== eventSet.length) {
        this.eventGroups_.push({
          type: 'Preceding events',
          tooltip: 'All events that have led to the selected one(s), ' +
                   'connected by flow arrows or by hierarchy.',
          selection: precedingEvents
        });
      }
      if (followingEvents.length !== eventSet.length) {
        this.eventGroups_.push({
          type: 'Following events',
          tooltip: 'All events that have been caused by the selected one(s), ' +
                   'connected by flow arrows or by call stack.',
          selection: followingEvents
        });
      }
      if (allEvents.length !== eventSet.length) {
        this.eventGroups_.push({
          type: 'All connected events',
          tooltip: 'All events connected to the selected one(s) by flow ' +
                   'arrows or by call stack.',
          selection: allEvents
        });
      }
    },

    addInFlowEvents_: function(event, eventSet) {
      if (!event.inFlowEvents)
        return;
      event.inFlowEvents.forEach(function(e) {
        eventSet.push(e);
      });
    },

    addOutFlowEvents_: function(event, eventSet) {
      if (!event.outFlowEvents)
        return;
      event.outFlowEvents.forEach(function(e) {
        eventSet.push(e);
      });
    },

    addAncestors_: function(event, eventSet) {
      if (!event.iterateAllAncestors)
        return;
      event.iterateAllAncestors(function(e) {
        eventSet.push(e);
      });
    },

    addDescendents_: function(event, eventSet) {
      if (!event.iterateAllDescendents)
        return;
      event.iterateAllDescendents(function(e) {
        eventSet.push(e);
      });
    },

    // Find the [first, last] index of the samples overlapping slice, assuming
    // samples are sorted. |last| is past-the-end so returned indices can be
    // used with Array.slice.
    findOverlappingSampleIndices_: function(samples, slice) {
      // Binary search. |test| is a function that should return true when we
      // need to explore the left branch and false to explore the right branch.
      function binSearch(test) {
        var i0 = 0;
        var i1 = samples.length;
        while (i0 < i1 - 1) {
          var i = Math.trunc((i0 + i1) / 2);
          if (test(i))
            i1 = i;  // Explore the left branch.
          else
            i0 = i;  // Explore the right branch.
        }
        return i1;
      }

      var first = binSearch(function(i) {
        return slice.start <= samples[i].start;
      });
      var sliceEnd = slice.start + slice.duration;
      var last = binSearch(function(i) {
        return sliceEnd < samples[i].start;
      });
      return [first, last];
    },

    addOverlappingSamples_: function(eventSet) {
      var samples = new tr.model.EventSet;
      eventSet.forEach(function(slice) {
        if (!slice.parentContainer || !slice.parentContainer.samples)
          return;
        var candidates = slice.parentContainer.samples;
        var filteredSamples = candidates.slice.apply(candidates,
            this.findOverlappingSampleIndices_(candidates, slice));
        filteredSamples.forEach(function(sample) {
          samples.push(sample);
        });
      }.bind(this));
      if (samples.length > 0) {
        this.eventGroups_.push({
          type: 'Overlapping samples',
          tooltip: 'All samples overlapping the selected slice(s).',
          selection: samples
        });
      }
    },

    updateContents_: function() {
      var table = this.$.table;
      if (this.eventGroups_ === undefined)
        table.tableRows = [];
      else
        table.tableRows = this.eventGroups_.slice();
      table.rebuild();
    }
  });
  </script>
</polymer-element>
