<commit_before>(function (Raphael) {
  Raphael.fn.graph = {};
  
  Raphael.fn.graph.enable = function (types)
  {
    // by default only extend circle
    if (!types) types = ['circle'];
    
    // extend given types
    for (var i = 0; i < types.length; i++)
    {
      var type = types[i];
      this[type] = function (paper, fn)
      {
        return function ()
        {
          var element = fn.apply(paper, arguments);
          element.graph = new GraphExtension(element);
          return element;
        };
      }(this, this[type]);
    }
    
    return this;
  }
    
  var GraphExtension = function (element)
  {
    this.element = element;
    this.paper = element.paper;
  }
  
  GraphExtension.prototype.graph = function (g)
  {
    return this._graph = g || this._graph;
  }

  GraphExtension.prototype.edgeTo = function (el, weight)
  {
    if (this.graph() && el.graph.graph() && this.graph() !== el.graph.graph()) {
      this.graph().each(function (v)
      {
        // copy this graph to el's graph
        for (var u in this.adj(v))
        {
          var edge = this.get(v, u);
          el.graph.graph().set(v, this.vertex(u), edge);
        }
      
        v.graph.graph(el.graph.graph());
      });
    
    } else {  
      // assign graph
      this.graph(el.graph.graph(this.graph() || el.graph.graph() || new Graph()));
    }
  
    // no loops, no multiedges
    if (this.element === el || this.graph().has(this.element, el))
      return;
  
    // create edge
    this.drawEdge(el);
  
    // attach listeners to redraw edges on drag
    this.setupVertex();
    el.graph.setupVertex();
    
    return this.element;
  }

  GraphExtension.prototype.edgesToRedraw = function ()
  {
    // edges (pairs) with any parent in the set
    
    if (!this.element.draggable) return;

    if (this.element.draggable.parent && this.element.draggable.parent._to_redraw)
    {
      return this.element.draggable.parent._to_redraw;
    }
  
    var to_redraw = []; // [[u, v], ...]
    var set_vertices = {}; // 
  
    for (var i = 0; i < this.element.draggable.parent.items.length; i++)
      set_vertices[this.element.draggable.parent.items[i]] = 1;
  
    this.graph().each(function (v)
    {
      for (var u in this.adj(v))
      {
        if (u < v && (v in set_vertices || u in set_vertices))
        {
          to_redraw.push([this.vertex(u), this.vertex(v)]);
        }
      }
    });
  
    return this.element.draggable.parent._to_redraw = to_redraw;
  }

  GraphExtension.prototype.setupVertex = function ()
  {
    if (!this.element.draggable) return;
    
    if (this._setup_vertex) return;
    this._setup_vertex = 1;
    
    // drag start
    this.element.mousedown(function (event)
    {
      if (event.shiftKey)
      {
        // create set or add to existing set
        var set = this.paper._set = this.paper._set || this.paper.set().draggable.enable();
        set.push(this);
        delete set._to_translate;
        delete set._to_redraw;
        this.attr('fill', 'green');
        this.graph.colorNeighbors('red');
      } else if (!this.graph.hasEnabledSet())
      {
        // check for current set
        if (this.paper._set)
        {
          var set = this.paper._set;
          delete this.paper._set;
          // disable the set
          set.draggable.disable();
          // return everything to original color
          this.graph.graph().each(function (v)
          {
            this.vertex(v).attr('fill', 'blue');
          });
        }
        // color neighbors the active-neighbor color
        this.graph.colorNeighbors('red');
      }
    });
  
    // dragging
    this.element.draggable.dragged(function ()
    {<commit_msg>added ability to remove from set with shift click<commit_after>(function (Raphael) {
  Raphael.fn.graph = {};
  
  Raphael.fn.graph.enable = function (types)
  {
    // by default only extend circle
    if (!types) types = ['circle'];
    
    // extend given types
    for (var i = 0; i < types.length; i++)
    {
      var type = types[i];
      this[type] = function (paper, fn)
      {
        return function ()
        {
          var element = fn.apply(paper, arguments);
          element.graph = new GraphExtension(element);
          return element;
        };
      }(this, this[type]);
    }
    
    return this;
  }
    
  var GraphExtension = function (element)
  {
    this.element = element;
    this.paper = element.paper;
  }
  
  GraphExtension.prototype.graph = function (g)
  {
    return this._graph = g || this._graph;
  }

  GraphExtension.prototype.edgeTo = function (el, weight)
  {
    if (this.graph() && el.graph.graph() && this.graph() !== el.graph.graph()) {
      this.graph().each(function (v)
      {
        // copy this graph to el's graph
        for (var u in this.adj(v))
        {
          var edge = this.get(v, u);
          el.graph.graph().set(v, this.vertex(u), edge);
        }
      
        v.graph.graph(el.graph.graph());
      });
    
    } else {  
      // assign graph
      this.graph(el.graph.graph(this.graph() || el.graph.graph() || new Graph()));
    }
  
    // no loops, no multiedges
    if (this.element === el || this.graph().has(this.element, el))
      return;
  
    // create edge
    this.drawEdge(el);
  
    // attach listeners to redraw edges on drag
    this.setupVertex();
    el.graph.setupVertex();
    
    return this.element;
  }

  GraphExtension.prototype.edgesToRedraw = function ()
  {
    // edges (pairs) with any parent in the set
    
    if (!this.element.draggable) return;

    if (this.element.draggable.parent && this.element.draggable.parent._to_redraw)
    {
      return this.element.draggable.parent._to_redraw;
    }
  
    var to_redraw = []; // [[u, v], ...]
    var set_vertices = {}; // 
  
    for (var i = 0; i < this.element.draggable.parent.items.length; i++)
      set_vertices[this.element.draggable.parent.items[i]] = 1;
  
    this.graph().each(function (v)
    {
      for (var u in this.adj(v))
      {
        if (u < v && (v in set_vertices || u in set_vertices))
        {
          to_redraw.push([this.vertex(u), this.vertex(v)]);
        }
      }
    });
  
    return this.element.draggable.parent._to_redraw = to_redraw;
  }

  GraphExtension.prototype.setupVertex = function ()
  {
    if (!this.element.draggable) return;
    
    if (this._setup_vertex) return;
    this._setup_vertex = 1;
    
    // drag start
    this.element.mousedown(function (event)
    {
      if (event.shiftKey)
      {
        // create set or get existing set
        var set = this.paper._set = this.paper._set || this.paper.set().draggable.enable();
        delete set._to_redraw;
        // gather other elements in the set
        var others = new Array();
        for (var i = 0; i < set.length; i++) {
          if (set[i] != this) {
            others.push(set[i]);
          }
        }
        if (others.length != set.length) {
          // disable old set
          set.draggable.disable();
          // create a new set without the element
          set = this.paper._set = this.paper.set().draggable.enable();
          for (var i = 0; i < others.length; i++) {
            set.push(others[i]);
          }
          this.attr('fill', 'blue');
          this.graph.colorNeighbors('blue');
        } else {
          // add this element to the set
          set.push(this);
          this.attr('fill', 'green');
          this.graph.colorNeighbors('red');
        }
      } else if (!this.graph.hasEnabledSet())
      {
        // check for current set
        if (this.paper._set)
        {
          var set = this.paper._set;
          delete this.paper._set;
          // disable the set
          set.draggable.disable();
          // return everything to original color
          this.graph.graph().each(function (v)
          {
            this.vertex(v).attr('fill', 'blue');
          });
        }
        // color neighbors the active-neighbor color
        this.graph.colorNeighbors('red');
      }
    });
  
    // dragging
    this.element.draggable.dragged(function ()
    {
{'fraction_non_alphanumeric': 0.14306820980054175, 'fraction_numerical': 0.0012312238364934746, 'mean_word_length': 1.8471784086926042, 'pattern_counts': {'":': 0, '<': 11, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5680962', 'n_tokens_mistral': 2598, 'n_tokens_neox': 2564, 'n_words': 557}