#################################
### COPYRIGHT: Anders Lyhagen ###
#################################


module CAUL_FAQS
module FlowAlongAux

  def self.convertToCLines(sel)
    es = sel.grep(Sketchup::Edge)
    gs = sel.grep(Sketchup::Group)
    convert(es) if es.length <= 2
    
    if gs.length > 0
      es = gs[0].entities.grep(Sketchup::Edge)
      convert(gs[0].entities, es) if es.length <= 2
    end
  end
  
  def self.convert(es)
    es.each { |e|
      e.parent.entities.add_cline(e.start.position, e.end.position)
      e.erase!
    }
  end

  def self.constructProjPlane(ent, sel)
    
    gs = sel.grep(Sketchup::Group)
    return if gs.length != 1
    
    bb = gs[0].bounds
    bb_min = bb.min
    bb_max = bb.max
    
    p0 = Geom::Point3d.new(bb_min.x, bb_max.y, bb_max.z)
    p1 = Geom::Point3d.new(bb_max.x, bb_max.y, bb_max.z)
    p2 = Geom::Point3d.new(bb_max.x, bb_max.y, bb_min.z)
    p3 = Geom::Point3d.new(bb_min.x, bb_max.y, bb_min.z)
    
    ng = ent.add_group
    ng.entities.add_face(p0, p3, p2, p1) 
  end
  
  #checks whether an egde is internal according to the conventional quad definition
  #http://sketchucation.com/forums/viewtopic.php?t=39442
  def self.convertDiagonal(sel)
    es = sel.grep(Sketchup::Edge)
    es.each { |e|
      e.soft=true
      e.smooth=true
      e.casts_shadows=false
    }
    
  end
  
  def self.addConstructionPoint(sel)
    es = sel.grep(Sketchup::Edge)
    return if es.length != 1
    e = es[0]
    v = e.start.position.z < e.end.position.z ? e.start : e.end
    e.parent.entities.add_cpoint(v.position)
  end
  
  ########################
  ### RECONSTRUCT PATH ###
  ########################
  
def self.getHorizontalRays(g)    
    es = g.entities.grep(Sketchup::Edge)
    hs = es.select { |e| (e.start.position.z - e.end.position.z).abs < 0.001 }
    hs.sort_by! { |e| e.start.position.z }
    return convertToRays(hs, g.transformation)
  end
  
  def self.convertToRays(es, tr)
    return es.map { |e|
      v = (e.end.position - e.start.position).transform!(tr).normalize!
      p = e.start.position.transform(tr)
      [p, v]
    }
  end

  def self.getPath(rays, es)
    ps = []
    rays.each { |ray|
      p = getIntersection(ray,  es)
      ps << p if p != nil
    }
    return ps
  end
  
  def self.getIntersection(ray, es)
    es.each { |e|
      p = Geom::intersect_line_line(ray, e.line)   
      return p if p != nil && onEdge(e, p) 
    }
    return nil
  end
  
  def self.onEdge(e, p)
    vp = (p - e.start.position)
    v = (e.end.position - e.start.position)
    return vp.dot(v) >= -0.000001 && vp.length <= v.length
  end
  
  def self.reshapePath(ent, sel)
    gs = sel.grep(Sketchup::Group)
    return if gs.length != 1	
   
    h_rays = getHorizontalRays(gs[0])
    es = sel.grep(Sketchup::Edge)
    return if es.length < 1
    ps = getPath(h_rays, es)
    res_g = ent.add_group
    (1..ps.length - 1).each { |i| res_g.entities.add_line(ps[i - 1], ps[i]) }
  end
  
  #######################
  

  def self.auxMain(mode)
    mod = Sketchup.active_model # Open model
    ent = mod.entities # All entities in model
    sel = mod.selection # Current selection
 
    mod.start_operation("FlowAux", true)
    if mode == 0 #Convert
      convertToCLines(sel)
    elsif mode == 1 #construct plane
      constructProjPlane(ent, sel)
    elsif mode == 2
      convertDiagonal(sel)
    elsif mode == 3
      addConstructionPoint(sel)
    elsif mode == 4
      reshapePath(ent, sel)
    end
    mod.commit_operation
  end
  
  #auxMain(4)
  

  #unless file_loaded?( __FILE__ )
 #   menu = UI.menu( 'Plugins' )
 #   sub = menu.add_submenu('FlowAlongQuadSrf')
 #   sub.add_item( 'Edge -> CLine' ) { self.auxMain 0}
#    sub.add_item( 'Proj Plane' ) { self.auxMain 1}
#    sub.add_item( 'Convert Diagonal' ) { self.auxMain 2}
#    sub.add_item( 'Add CPoint' ) { self.auxMain 3}
#  end
 
#  file_loaded( __FILE__ )

  
  
end
end
