Beispiel #1
0
    def process_intersection(self, a, b):
        '''
        Usada para processar a interseção entre dois eventos. 
        '''
        if a == None or b == None or a == b: return
        if a.type == INTERSECTION or b.type == INTERSECTION: return

        a_line = a.segment.plot(cor='blue')
        b_line = b.segment.plot(cor='blue')
        control.sleep()
        control.plot_delete(a_line)
        control.plot_delete(b_line)

        # Ponto de interseção
        p = segment_intersection(a, b)
        if p == None: return
        # Ponto ja foi processado, adiciono possiveis novos segmentos a inter
        if p in self.intersections:
            self.intersections[p].add(a)
            self.intersections[p].add(b)
            return

        p_plot = point.Point(p[0], p[1])
        p_plot.plot('white')

        # Cria conjunto com os segmentos que compõem aquela interseção
        self.intersections[p] = {a, b}
        # Adiciono a interseção na fila de eventos se ela esta a direita
        if p[0] >= self.current_x:
            new_event = Event(INTERSECTION, p, None)
            self.bag.insert(p, new_event)
Beispiel #2
0
def Bent_ott(segments):
    '''
    Rotina principal de execução do algoritmo de Bentley and Ottmman.
    '''
    # Ordenando os pontos do segmento
    for s in segments:
        if s[0] > s[1]:
            s.to, s.init = s.init, s.to
        s.plot()

    bag = EventBag(segments)
    sweep_line = SweepLine(bag)
    line = None
    while not bag.event_bag.is_empty():
        p, e_tuple = bag.next_events()
        # Andando com a linha de varredura
        if line: control.plot_delete(line)
        sweep_line.current_x = p[0]
        line = control.plot_vert_line(p[0], color='yellow')
        control.sleep()
        # Processando cada tupla de eventos do mesmo tipo
        for t in [END, INTERSECTION, START, VERTICAL]:
            for e in e_tuple[t]:
                sweep_line.process_event(e)

    intersections = sweep_line.get_intersections()
    print("Numero de interseções: " + str(len(intersections)))
Beispiel #3
0
    def __caseC(self, currentVertex):
        self.__stack.pop()

        while (self.__stackSize() > 1):
            control.sleep()
            self.__addDiagonal(currentVertex)
            self.__stack.pop()
Beispiel #4
0
    def update(self, a, b):
        '''
        função auxiliar que recebe 2 pontos e atualiza o melhor caso necessario
        a, b: pontos candidatos
        '''

        a_id = a.hilight(color='cyan')
        b_id = b.hilight(color='cyan')
        l_id = a.lineto(b, color='cyan')
        control.sleep()
        d = a.distance_to(b)
        if d < EPS: d = 0
        if d < self.best[0][2]:

            # atualizando visualização
            control.sleep()
            if self.best[1][0] != None:
                self.best[0][0].unhilight(self.best[1][0])
            if self.best[1][1] != None:
                self.best[0][1].unhilight(self.best[1][1])
            if self.best[1][2] != None:
                self.best[0][0].remove_lineto(self.best[0][1], self.best[1][2])

            self.best[0][0] = a
            self.best[0][1] = b
            self.best[0][2] = d
            self.best[1][0] = a.hilight(color='green')
            self.best[1][1] = b.hilight(color='green')
            self.best[1][2] = a.lineto(b, color='green')

        a.unhilight(a_id)
        b.unhilight(b_id)
        a.remove_lineto(b, l_id)
        return d
Beispiel #5
0
def recursive_ham_sandwich(G1, G2, p1, p2, T):
    if len(G1) < len(G2):
        return recursive_ham_sandwich(G2, G1, p2, p1, T)
    T, is_base = new_interval(G1, G2, p1, p2, T)

    if is_base:
        valid_answers = []
        for g in G1:
            for h in G2:
                p = g.intersect(h)
                if p and isinstance(p.dual(), Line):
                    valid_answers.append(p.dual())
        return valid_answers, G1 + G2

    t = new_trapezoid(G1, p1, T)
    t_ids = []
    control.freeze_update()
    for i in range(4):
        j = (i + 1) % 4
        t_ids.append(
            control.plot_segment(t[i].x, t[i].y, t[j].x, t[j].y, 'yellow'))
    control.sleep()
    control.thaw_update()

    G1, p1 = discard_lines(G1, p1, t)
    G2, p2 = discard_lines(G2, p2, t)

    for id in t_ids:
        control.plot_delete(id)

    return recursive_ham_sandwich(G1, G2, p1, p2, T)
Beispiel #6
0
def monotonos (d, P, diags):
    """ Função que recebe um polígono P e particiona P em vários polígonos monótonos
        Através da inserção de diagonais
        Coloca as diagonais na DCEL d
    """
    # Ordena os vértices pela Y-coordenada
    v = P.vertices()
    v = sorted(v, key = lambda x:(-x.y))
    
    L = Abbb()
    
    # os vértices são os pontos eventos da linha de varredura
    for p in v:
        p.hilight()
        h = control.plot_horiz_line (p.y)
        control.sleep()
        
        viz_cima = p.next
        viz_baixo = p.prev
        if viz_cima.y < viz_baixo.y:
            viz_cima, viz_baixo = viz_baixo, viz_cima
        
        if viz_cima.y > p.y and p.y > viz_baixo.y:
            trata_caso_meio (p, viz_baixo, L, d, diags)
        elif viz_cima.y < p.y:
            trata_ponta_pra_cima (p, L, d, diags)
        else:
            trata_ponta_pra_baixo (p, L, d, diags) 
        
        control.plot_delete (h)
        p.unhilight()
Beispiel #7
0
    def __partitionatePolygon(self):
        BST = bst.SplayTree()

        for eventVertex in sorted(self.dcel.vertex):
            vertexNumber = eventVertex.vertexNumber()
            previousVertexNumber = self.dcel.iterateVertex(vertexNumber - 1)
            nextVertexNumber = self.dcel.iterateVertex(vertexNumber + 1)

            previousVertex = self.dcel.getVertex(previousVertexNumber)
            nextVertex = self.dcel.getVertex(nextVertexNumber)

            sweepLineId = control.plot_horiz_line(eventVertex.y, color="cyan")
            suppPointId = eventVertex.coordinates.hilight(color="white")
            control.sleep()

            if (previousVertex.y > eventVertex.y and nextVertex.y > eventVertex.y) or\
                    (eventVertex.y == nextVertex.y and nextVertex.x < eventVertex.x and previousVertex.y > eventVertex.y) or\
                    (eventVertex.y == previousVertex.y and previousVertex.x < eventVertex.x and nextVertex.y > eventVertex.y):
                self.__caseThree(BST, eventVertex)
            elif (previousVertex.y < eventVertex.y and nextVertex.y < eventVertex.y) or\
                    (eventVertex.y == nextVertex.y and eventVertex.y > previousVertex.y and eventVertex.x < nextVertex.x) or\
                    (eventVertex.y == previousVertex.y and eventVertex.y > nextVertex.y and eventVertex.x < previousVertex.x):
                self.__caseTwo(BST, previousVertex, eventVertex, nextVertex)
            else:
                self.__caseOne(BST, previousVertex, eventVertex, nextVertex)

            control.plot_delete(sweepLineId)
            control.plot_delete(suppPointId)
Beispiel #8
0
    def __triangulate(self):
        self.__stack.append(self.__sortedVertexes[0])
        self.__stack.append(self.__sortedVertexes[1])

        for i in range(2, len(self.__sortedVertexes)):
            adjacentVertexes = self.__getAdjacentVertexes(i)
            currentVertex = self.__sortedVertexes[i]
            suppPointId = currentVertex.coordinates.hilight(color="white")

            stackBase = self.__stackBase()
            stackTop = self.__stackTop()
            neighborFromBase = self.__isVertexNeighborFrom(
                adjacentVertexes, stackBase)
            neighborFromTop = self.__isVertexNeighborFrom(
                adjacentVertexes, stackTop)

            if (neighborFromTop and not neighborFromBase):
                self.__caseA(currentVertex)
            elif (not neighborFromTop and neighborFromBase):
                self.__caseB(currentVertex)
            elif (neighborFromTop and neighborFromBase):
                self.__caseC(currentVertex)

            control.sleep()
            control.plot_delete(suppPointId)
Beispiel #9
0
def trata_ponta_pra_cima (p, L, dcel, diags):
    viz_esq = p.next
    viz_dir = p.prev
    if left (p, viz_dir, viz_esq):
        viz_esq, viz_dir = viz_dir, viz_esq
    
    t = Trapezio (p)
    removido = (L.busca (t)).elemento
    
    if removido == None:
        t.a_esq = Segment (p, viz_esq)
        t.a_dir = Segment (p, viz_dir)
        t.desenha()
        L.insere (t)
    
    else:
        L.deleta (t)
        removido.apaga()
        d = Segment (p, removido.sup)
        d.plot('blue')
        dcel.add_edge (d.init, d.to)
        diags.append(d)
        control.sleep()
        
        
        t1 = Trapezio (p, removido.a_esq, Segment (p, viz_esq))
        t2 = Trapezio (p, Segment (p, viz_dir), removido.a_dir)
        t1.desenha()
        t2.desenha()
        L.insere (t1)
        L.insere (t2)
        
    control.sleep()
Beispiel #10
0
def trata_caso_meio (p, viz_baixo, L, dcel, diags):
    # Remove da linha o trapésio que tem o p
    t = Trapezio (p)
    removido = (L.busca (t)).elemento
    removido.apaga()
    L.deleta (t)
    
    if ponta_pra_baixo (removido.sup):
        d = Segment (removido.sup, p)
        d.plot('blue')
        dcel.add_edge (d.init, d.to)
        diags.append(d)
        control.sleep()
        
    # Insere um novo trapésio com o p
    # Se o removido estava a direita
    if (p == removido.a_dir.to):
        t.a_dir = Segment (p, viz_baixo)
        t.a_esq = removido.a_esq        
    # Se estava a esquerda
    else:
        t.a_esq = Segment (p, viz_baixo)
        t.a_dir = removido.a_dir
    t.desenha()
    L.insere (t)
    control.sleep()
Beispiel #11
0
def find_destine(pt):
    global DG, root
    visited = set()
    stack = [root]
    visited.add(root)
    found = None
    while (found is None):
        node = stack[-1]
        if (node in visited):
            node.draw()
            control.sleep()
            f = False
            for nd in DG.adj[node]:
                if (nd not in visited):
                    node.remove_draw()
                    stack.append(nd)
                    f = True
                    break
            if (f): continue
            #At this point: node is the leaf!
        else:
            if not node.contains_proper(pt) and not node.is_on_edge(pt):
                # node subtree does not contain pt
                stack.pop()
            visited.add(node)
            continue
        found = node
    found.remove_draw()
    degen = found.is_on_edge(pt)
    return degen, found
Beispiel #12
0
def trataCaso2(u,v,w,arvore,vertices,diagonais,faces):
    if(left(u,v[0],w)): # u<=>w
        aux = w
        w = u
        u = aux

    aux = arvore.get(v[0])
    arvore.delete(v[0])

    if(aux is None):
        #print bcolors.OKBLUE,"Inseri um trapézio com vértice de apoio ", v,": ",Segment(v[0],u),Segment(v[0],w),bcolors.ENDC
        arvore.insert( ( Segment(v[0],u),v,Segment(v[0],w) ) )
    else:
        trap = aux.trap
        #print bcolors.OKBLUE,"Inseri dois trapézios com vértice de apoio ", v ,": ",trap[0],Segment(v[0],u)," E ",Segment(v[0],w),trap[2],bcolors.ENDC
        arvore.insert( (Segment(v[0],w),v,trap[2]) )  #insiro esse primeiro para respeitar a ordem correta na arvore(dado que eu escolhi comparar por x do vertice de apoio
        arvore.insert( (trap[0],v,Segment(v[0],u)) )

        diagonais.append( Segment(trap[1][0],v[0]) )

        aresta =  Aresta()
        aresta.setAresta(Segment(trap[1],v))
        aresta2 = Aresta()
        aresta2.setAresta(Segment(v,trap[1]))
        
        aresta.setGemeo(aresta2)
        aresta2.setGemeo(aresta)

        Segment(trap[1][0],v[0]).hilight("blue")
        control.sleep()
        insereDiagonal(vertices[trap[1][1]-1],vertices[v[1]-1],aresta,faces)
Beispiel #13
0
def trataCaso1(u,v,w,arvore,pontos,vertices,diagonais,faces):
    if(u.y < w.y): #u <=> w
        aux = w
        w = u 
        u = aux

    aux = (arvore.get(v[0])).trap #aux recebe um trapézio que contem v
    arvore.delete(v[0])
        
    if(v[0].x == aux[0].to.x and v[0].y == aux[0].to.y): 
        arvore.insert((Segment(v[0],w),v,aux[2]))
        #print bcolors.OKBLUE,"Inseri um trapézio com vértice de apoio", v," : ",Segment(v[0],w),aux[2],bcolors.ENDC
    else:
        arvore.insert((aux[0],v,Segment(v[0],w)))
        #print bcolors.OKBLUE,"Inseri um trapézio com vértice de apoio ",v,": ",aux[0],Segment(v[0],w),bcolors.ENDC

    if(pontaParaBaixo(aux[1],pontos)):
        diagonais.append(Segment(aux[1][0],v[0]))

        aresta = Aresta()
        aresta.setAresta(Segment(aux[1],v))
        aresta2 = Aresta()
        aresta2.setAresta(Segment(v,aux[1]))

        aresta.setGemeo(aresta2)
        aresta2.setGemeo(aresta)

        Segment(aux[1][0],v[0]).hilight("blue")
        control.sleep()
        insereDiagonal(vertices[aux[1][1]-1],vertices[v[1]-1],aresta,faces)
Beispiel #14
0
def marca_intersec (no1, no2, pontos, x = None):
    "Testa se há interseção entre o nó1 e o nó2 e adiciona em pontos, se houver"
    "E só marca as interseções que ocorrem do x pra direita"
    
    # Despinta de verde e pinta de amarelo
    no1.seg.hide()
    no2.seg.hide()
    no1.seg.plot ("yellow")
    no2.seg.plot ("yellow")
    control.sleep()
    # despinta de amarelo e pinta de verde denovo
    no1.seg.hide()
    no2.seg.hide()
    no1.seg.plot ("green")
    no2.seg.plot ("green")
    
    p = no1.seg.intersection (no2.seg)
    # Só marco se o o ponto esta pra frente do x especificado
    if (p != None and (x == None or p.x > x)):
        # Crio o nó
        p_no = Node_Point (p, ini = [], fim = [], inter = [no1, no2])
            
        # insere o ponto na arvore, ou só atualiza se ele já existir
        p_no_abb = pontos.busca (p_no)
        if p_no_abb.elemento == None:
            pontos.insere (p_no)
            p_no.ponto.plot('blue') 
        else:
            if no1 not in p_no_abb.elemento.inter:
                p_no_abb.elemento.inter.append (no1)
            if no2 not in p_no_abb.elemento.inter:
                p_no_abb.elemento.inter.append (no2)
                    
    control.sleep()
def update(a, b, best):
    '''
    a, b: pontos candidatos
    best: melhores pontos encontrados
    '''

    a_id = a.hilight(color='blue')
    b_id = b.hilight(color='blue')
    l_id = a.lineto(b, color='blue')
    control.sleep()

    d = a.distance_to(b)
    if d < best[0][2]:

        # atualizando visualização
        control.sleep()
        if best[1][0] != None:
            best[0][0].unhilight(best[1][0])
        if best[1][1] != None:
            best[0][1].unhilight(best[1][1])
        if best[1][2] != None:
            best[0][0].remove_lineto(best[0][1], best[1][2])

        best[0][0] = a
        best[0][1] = b
        best[0][2] = d
        best[1][0] = a.hilight(color='green')
        best[1][1] = b.hilight(color='green')
        best[1][2] = a.lineto(b, color='green')
    
    a.unhilight(a_id)
    b.unhilight(b_id)
    a.remove_lineto(b, l_id)
Beispiel #16
0
def Lee_Preparata (p):
    
    P = p[0]
    diags = []
    d = Dcel ()
    d.initPolygon (P)
    
    # Atualiza a DCEL colocando as diagonais parar a partição em monótonos
    monotonos (d, P, diags)
    n_face_externa = len(P.vertices())
    divisoras = len(diags)
    # Para cada face, constrói um polígono e triangula ele

    if len (d.f) == 2:
        return Monotono([P])

    for e in d.f:
        vertices = [e.init]
        while e.to != vertices[0]:
            vertices.append (e.to)
            e = e.prox
        if len(vertices) != n_face_externa:
            new_p = Polygon (vertices)
            new_p.plot("orange")
            control.sleep()
            # Triangula o new_p e adiciona as novas diagonais no diags
            diags.extend (Monotono ([new_p]))
            new_p.hide()
    
    # despinta as arestas
    for i in range(divisoras):
        diags[i].hide()
        diags[i].plot("green")
Beispiel #17
0
def trataCaso3(v,arvore,pontos,vertices,diagonais,faces):
    aux = (arvore.get(v[0])).trap
    arvore.delete(v[0])

    if(pontaParaBaixo(aux[1],pontos)):#aux[1] = vertice de apoio do trapézio
        diagonais.append(Segment(aux[1][0],v[0]))

        aresta = criaAresta(aux[1],v)

        Segment(aux[1][0],v[0]).hilight("blue")
        control.sleep()
        insereDiagonal(vertices[aux[1][1]-1],vertices[v[1]-1],aresta,faces)

    
    if( ((aux[0].to.x != v[0].x and aux[0].to.y != v[0].y) or (aux[2].init.x != v[0].x and aux[2].init.y != v[0].y)) ):#caso tenham 2 trapézios com v 
        aux2 =  arvore.get(v[0]) #segundo trapexio que contem v
        if(aux2):
            aux2 = aux2.trap
            arvore.delete(v[0])

            if(pontaParaBaixo(aux2[1],pontos)): #aux2[1] = vertice de apoio do segundo trapézio
                diagonais.append(Segment(aux2[1][0],v[0]))

                aresta = criaAresta(aux2[1],v)

                Segment(aux2[1][0],v[0]).hilight("blue")            
                control.sleep()
                insereDiagonal(vertices[aux2[1][1]-1],vertices[v[1]-1],aresta,faces)

            if( aux[2].to.x == v[0].x and aux[2].to.y == v[0].y):
                arvore.insert( (aux[0],v,aux2[2]) )
            else:
                arvore.insert( (aux2[0],v,aux[2]) )
	def visit(self, u, target):
		u.setVisited(True)
		v = self.findNeighbor(u)
		while v is not None:

			# Printando o segmento atual do grafo
			seg = Segment(Point(u.x, u.y), Point(v.x, v.y))
			seg.plot('cyan')
			control.sleep()

			# Continuar o DFS
			if (v == target):
				self.solved = True
				return 1
			self.visit(v, target)

			# Condicao de parada do DFS
			if(self.solved):
				return 1

			# Retirando o print do segmento
			seg.hide()
			control.sleep()

			# Pegar o próximo vizinho
			v = self.findNeighbor(u)
def Brute_Force(segmentos):
    
    cores = (config.COLOR_ALT1, config.COLOR_ALT7, config.COLOR_ALT6)
    
    for segmento in segmentos:
        segmento.intersected = False
    
    for i in range (len(segmentos)):
        control.freeze_update ()
        hii = segmentos[i].hilight2 (cores[1])
        control.thaw_update ()
        control.sleep()
        for j in range (i + 1, len (segmentos)):
            control.freeze_update ()
            hij = segmentos[j].hilight2(cores[0])
            control.thaw_update ()
            control.sleep()
            if prim.inter(segmentos[i],segmentos[j]):
                control.freeze_update ()
                segmentos[i].hilight2 (cores[2])
                segmentos[j].hilight2 (cores[2])
                segmentos[i].intersected = True
                segmentos[j].intersected = True
                control.thaw_update ()
            segmentos[j].unhilight (hij)
        segmentos[i].unhilight (hii)
Beispiel #20
0
def visGraphAlg(l):
	poligs = leEntrada(l)

	robo = poligs[0]
	destino = None

	desenhaTudo(l) #Muito codigo igual ao de baixo...mas deixa

	if(len(robo) == 1):
		print("Robo ponto na posicao ", robo[0]) 
		probo = robo[0]
		destino = poligs[1][0] #Suponho ser um ponto
	else:
		robo = Robo(robo)
		probo = poligs[1][0] # Suponho ser um ponto
		poligs.pop(0) #Removo o polígono do robo da lista, iremos tratar só com o ponto
		destino = poligs[1][0] # Suponho ser um ponto
		for i in range(len(poligs)):
			if(len(poligs[i]) > 1):
				poligs[i] = robo.deformaPolig(poligs[i])
				Polygon(poligs[i]).plot()
				control.sleep()

	pontos = []
	for i in range(len(poligs)):
		poligs[i] = Polygon(poligs[i])
		poligs[i].hilight()
		pontos.extend(poligs[i].to_list())
		control.sleep()


	probo.prev = probo.__next__ = probo

	
	
	compara = criaCompara(probo)
	pontos.sort(key = cmp_to_key(compara), reverse = True)

	
	#Grafo
	G = Grafo(len(pontos))

	#Numerando os pontos
	for i in range(len(pontos)):
		pontos[i].i = i;

	for pi in pontos:
		W = verticesVisiveis(pi, poligs)
		for pj in W:
			G.addAresta(pi.i,pj.i, dist2(pi,pj)**0.5)
		



	path, dist = G.dijkstra(probo.i, destino.i)
	for i in range(len(path)-1):
		v = path[i]; u = path[i+1]
		pontos[v].lineto(pontos[u], 'red')
Beispiel #21
0
def add_to_normal_case(par, pt):
    global DG, dcel
    # adds three new triangles to Digraph
    verts = par.get_vertices()  #parent vertices counter-clockwise
    #new triangles -> already counter-clockwise
    new_t1 = Node(verts[0], verts[1], pt)
    new_t2 = Node(verts[1], verts[2], pt)
    new_t3 = Node(verts[2], verts[0], pt)
    DG.add_node(new_t1)
    DG.add_node(new_t2)
    DG.add_node(new_t3)
    DG.add_edge(par, new_t1)
    DG.add_edge(par, new_t2)
    DG.add_edge(par, new_t3)

    # updates the DCEL
    h1_1 = hedge(verts[1], pt)
    h1_2 = hedge(pt, verts[0])
    h1_3 = dcel.get_hedge((verts[0], verts[1]))
    h1_1.set_data(new_t1, h1_3, h1_2)
    h1_2.set_data(new_t1, h1_1, h1_3)
    h1_3.set_data(new_t1, h1_2, h1_1)
    dcel.add_hedge(h1_1)
    dcel.add_hedge(h1_2)

    h2_1 = hedge(verts[2], pt)
    h2_2 = hedge(pt, verts[1])
    h2_3 = dcel.get_hedge((verts[1], verts[2]))
    h2_1.set_data(new_t2, h2_3, h2_2)
    h2_2.set_data(new_t2, h2_1, h2_3)
    h2_3.set_data(new_t2, h2_2, h2_1)
    dcel.add_hedge(h2_1)
    dcel.add_hedge(h2_2)

    h3_1 = hedge(verts[0], pt)
    h3_2 = hedge(pt, verts[2])
    h3_3 = dcel.get_hedge((verts[2], verts[0]))
    h3_1.set_data(new_t3, h3_3, h3_2)
    h3_2.set_data(new_t3, h3_1, h3_3)
    h3_3.set_data(new_t3, h3_2, h3_1)
    dcel.add_hedge(h3_1)
    dcel.add_hedge(h3_2)

    dcel.get_hedge((verts[2], pt)).face.draw()
    dcel.get_hedge((verts[1], pt)).face.draw()
    dcel.get_hedge((verts[0], pt)).face.draw()
    control.sleep()
    dcel.get_hedge((verts[2], pt)).face.remove_draw()
    dcel.get_hedge((verts[1], pt)).face.remove_draw()
    dcel.get_hedge((verts[0], pt)).face.remove_draw()

    for he in [h1_1, h2_1, h3_1]:
        if he.face != he.next.face or\
            he.face != he.prev.face:
            print("BIG PROBLEM NUMBER 2")

    return [new_t1, new_t2, new_t3]
Beispiel #22
0
 def draw_interval(should_plot=True):
     control.thaw_update()
     for i in range(2):
         if not ids[i] == None:
             control.plot_delete(ids[i])
         if T[i] != -inf and T[i] != +inf and should_plot:
             ids[i] = control.plot_vert_line(T[i], 'yellow')
     control.sleep()
     control.freeze_update()
Beispiel #23
0
def Incr(l):
    dag = DAG()
    for pt in l:
        pt.hilight()
        control.sleep()
        dag.insert(pt)
        pt.unhilight()
    print(DAG.to_graph(dag))
    return dag
Beispiel #24
0
def delete_stuff(stuff):
    control.freeze_update()
    for s in stuff:
        if isinstance(s, Line):
            control.plot_delete(s.plot_id)
        else:
            s.tk.unplot()
    control.sleep()
    control.thaw_update
Beispiel #25
0
    def __caseA(self, currentVertex):
        isTopNextOrder = self.__stackTop().vertexNumber() == self.__dcel.iterateVertex(
            currentVertex.vertexNumber() + 1)

        while (self.__stackSize() > 1 and self.__angle(currentVertex, isTopNextOrder)):
            control.sleep()
            self.__stack.pop()
            self.__addDiagonal(currentVertex)

        self.__stack.append(currentVertex)
Beispiel #26
0
def pontosRepetidos(l):
    " Verifica se há pontos coincidentes em l "
    for i in range(1, len(l)):
        l[i].hilight('green')
        control.sleep()
        if l[i] == l[i - 1]:
            l[i].hilight('red')
            return True
        l[i].unhilight()
    return False
Beispiel #27
0
def e_lineto(p, q, color=config.COLOR_PRIM):
    if max(p.inf, q.inf) > 0:
        return
    keep = p.inner.lineto(q.inner, color)

    control.thaw_update()
    control.update()
    control.freeze_update()
    control.sleep()

    p.inner.remove_lineto(q, keep)
Beispiel #28
0
def Reflex(ui, st, stt):
	ui.origin.lineto(stt.origin, 'yellow')
	control.sleep ()
	ui.origin.remove_lineto(stt.origin)

	if(collinear(st.origin, stt.origin, ui.origin)):
		return 1

	if(st.rightSide):
		return left_on(stt.origin, st.origin, ui.origin)
	return right_on(stt.origin, st.origin, ui.origin)
Beispiel #29
0
def mergehull_rec (l):
	"""Funcao recursiva que implementa o Merge Hull

	Retorna os pontos com coordenada x minima e maxima do fecho convexo
	encontrado, alem do proprio fecho.
	"""
	n = len (l)
	if n == 1:
		#l[0].prev = l[0].next = l[0]
		pol = Polygon ( [ l[0] ] )
		pol.plot ()
		#control.sleep ()
		return (l[0], l[0], pol)
	
	# Divisao
	l1 = l[:n/2]
	l2 = l[n/2:]

	id = control.plot_vert_line ((l2[0].x + l1[-1].x) / 2.)
	control.sleep ()

	# Conquista
	ch1 = mergehull_rec (l1)

	ch2 = mergehull_rec (l2)

	v = ch1[1]
	u = ch2[0]

	control.plot_delete (id)

	# Combinar
	sup = superior_tangent (v, u)
	id_sup = sup[0].lineto (sup[1], config.COLOR_ALT1)
	inf = inferior_tangent (v, u)
	id_inf = inf[0].lineto (inf[1], config.COLOR_ALT1)

	control.freeze_update ()
	control.plot_delete (id_sup)
	control.plot_delete (id_inf)
	ch1[2].hide ()
	ch2[2].hide ()

	sup[0].prev = sup[1]
	sup[1].next = sup[0]

	inf[0].next = inf[1]
	inf[1].prev = inf[0]

	ch1[2].pts = inf[0]
	ch1[2].plot ()
	control.thaw_update ()

	return (ch1[0], ch2[1], ch1[2])
Beispiel #30
0
def Reflex(ui, st, stt):
    ui.origin.lineto(stt.origin, "yellow")
    control.sleep()
    ui.origin.remove_lineto(stt.origin)

    if collinear(st.origin, stt.origin, ui.origin):
        return 1

    if st.rightSide:
        return left_on(stt.origin, st.origin, ui.origin)
    return right_on(stt.origin, st.origin, ui.origin)
Beispiel #31
0
    def __caseB(self, currentVertex):
        aux = self.__stackTop()

        while (self.__stackSize() > 1):
            control.sleep()
            self.__addDiagonal(currentVertex)
            self.__stack.pop()

        self.__stack.pop()
        self.__stack.append(aux)
        self.__stack.append(currentVertex)
    def needs_fix(self, other):
        # inter are the edges self and other have in common
        inter, dif = self.get_relative_vertices(other)
        # check if quad is convex
        if (len(inter) != 2 or len(dif) != 2):
            print("ERRO NA LEGALIZACAO")
            exit(1)
        if self.v1 in inter:
            if self.v2 in inter:
                inter_0 = self.v1
                inter_1 = self.v2
                dif_0 = self.v3
            else:
                inter_0 = self.v3
                inter_1 = self.v1
                dif_0 = self.v2
        else:
            inter_0 = self.v2
            inter_1 = self.v3
            dif_0 = self.v1
        if other.v1 in inter:
            if other.v2 in inter:
                dif_1 = other.v3
            else:
                dif_1 = other.v2
        else:
            dif_1 = other.v1

        if not left(inter_0, inter_1, dif_1):
            aux = dif_0
            dif_0 = dif_1
            dif_1 = aux
        convex = left(inter_0, dif_0, inter_1) and\
                 left(dif_0, inter_1, dif_1) and\
                 left(inter_1, dif_1, inter_0) and\
                 left(dif_1, inter_0, dif_0)

        if not convex: return False
        # check if inter is best
        # only draws if passes convex
        self.draw("#ffaa33")
        other.draw("#ffaa33")
        did = control.plot_segment(inter_0.x, inter_0.y, inter_1.x,\
                                   inter_1.y, color="#ffffff")
        control.sleep()
        control.plot_delete(did)
        self.remove_draw()
        other.remove_draw()

        C = Circle(inter_0, inter_1, dif_0)
        C.draw()
        control.sleep()
        C.remove_draw()
        return C.is_inside(dif_1)
Beispiel #33
0
def mergehull_rec(l):
    """Funcao recursiva que implementa o Merge Hull

	Retorna os pontos com coordenada x minima e maxima do fecho convexo
	encontrado, alem do proprio fecho.
	"""
    n = len(l)
    if n == 1:
        #l[0].prev = l[0].next = l[0]
        pol = Polygon([l[0]])
        pol.plot()
        #control.sleep ()
        return (l[0], l[0], pol)

    # Divisao
    l1 = l[:n // 2]
    l2 = l[n // 2:]

    id = control.plot_vert_line((l2[0].x + l1[-1].x) / 2.)
    control.sleep()

    # Conquista
    ch1 = mergehull_rec(l1)

    ch2 = mergehull_rec(l2)

    v = ch1[1]
    u = ch2[0]

    control.plot_delete(id)

    # Combinar
    sup = superior_tangent(v, u)
    id_sup = sup[0].lineto(sup[1], config.COLOR_ALT1)
    inf = inferior_tangent(v, u)
    id_inf = inf[0].lineto(inf[1], config.COLOR_ALT1)

    control.freeze_update()
    control.plot_delete(id_sup)
    control.plot_delete(id_inf)
    ch1[2].hide()
    ch2[2].hide()

    sup[0].prev = sup[1]
    sup[1].next = sup[0]

    inf[0].next = inf[1]
    inf[1].prev = inf[0]

    ch1[2].pts = inf[0]
    ch1[2].plot()
    control.thaw_update()

    return (ch1[0], ch2[1], ch1[2])
Beispiel #34
0
def draw_triang(pt1, pt2, pt3):
    seg1 = segment.Segment(pt1, pt2)
    seg2 = segment.Segment(pt1, pt3)
    seg3 = segment.Segment(pt2, pt3)
    seg1.hilight("yellow")
    seg2.hilight("yellow")
    seg3.hilight("yellow")
    control.sleep()
    seg1.unhilight()
    seg2.unhilight()
    seg3.unhilight()
Beispiel #35
0
def add_triangs_dcel(d, p, triang):
    " Adiciona o P na dcel d e uma aresta de p pra cada ponta do triang "
    d.add_vertex(p)
    e1 = d.add_edge(p, triang.p1, triang.a.f)
    e2 = d.add_edge(p, triang.p2, triang.a.f)
    e3 = d.add_edge(p, triang.p3, e2.f)
    e1.draw(color_novo)
    e2.draw(color_novo)
    e3.draw(color_novo)
    sleep()
    return e1, e2, e3
Beispiel #36
0
def visGraphAlg(l):
    poligs = leEntrada(l)

    robo = poligs[0]
    destino = None

    desenhaTudo(l)  #Muito codigo igual ao de baixo...mas deixa

    if (len(robo) == 1):
        print("Robo ponto na posicao ", robo[0])
        probo = robo[0]
        destino = poligs[1][0]  #Suponho ser um ponto
    else:
        robo = Robo(robo)
        probo = poligs[1][0]  # Suponho ser um ponto
        poligs.pop(
            0
        )  #Removo o polígono do robo da lista, iremos tratar só com o ponto
        destino = poligs[1][0]  # Suponho ser um ponto
        for i in range(len(poligs)):
            if (len(poligs[i]) > 1):
                poligs[i] = robo.deformaPolig(poligs[i])
                Polygon(poligs[i]).plot()
                control.sleep()

    pontos = []
    for i in range(len(poligs)):
        poligs[i] = Polygon(poligs[i])
        poligs[i].hilight()
        pontos.extend(poligs[i].to_list())
        control.sleep()

    probo.prev = probo.__next__ = probo

    compara = criaCompara(probo)
    pontos.sort(key=cmp_to_key(compara), reverse=True)

    #Grafo
    G = Grafo(len(pontos))

    #Numerando os pontos
    for i in range(len(pontos)):
        pontos[i].i = i

    for pi in pontos:
        W = verticesVisiveis(pi, poligs)
        for pj in W:
            G.addAresta(pi.i, pj.i, dist2(pi, pj)**0.5)

    path, dist = G.dijkstra(probo.i, destino.i)
    for i in range(len(path) - 1):
        v = path[i]
        u = path[i + 1]
        pontos[v].lineto(pontos[u], 'red')
Beispiel #37
0
def sweep_line(input_segments):
    bst = BinarySearchTree()
    event_queue = EventQueue(input_segments)

    for event_point in event_queue:
        sweep_line_id = control.plot_vert_line(
            event_point.segment.init.x
            if event_point.is_left else event_point.segment.to.x,
            color="cyan")
        bst.reset_above_below_state()

        if event_point.is_left:
            event_point.segment.hilight(color_line="blue", color_point="blue")
            control.sleep()
            bst.insert(event_point.segment)
            bst.find_above_below(event_point.segment)
            intersect_above = event_point.segment.intersects(
                bst.above.data) if bst.above is not None else False
            intersect_below = event_point.segment.intersects(
                bst.below.data) if bst.below is not None else False

            if (intersect_above or intersect_below):
                event_point.segment.hilight(color_line="yellow",
                                            color_point="yellow")

                if intersect_above:
                    bst.above.data.hilight(color_line="yellow",
                                           color_point="yellow")
                elif intersect_below:
                    bst.below.data.hilight(color_line="yellow",
                                           color_point="yellow")

                return True
        elif not event_point.is_left:
            control.sleep()
            bst.find_above_below(event_point.segment)
            intersect_above_below = bst.below.data.intersects(
                bst.above.data) if (bst.below is not None
                                    and bst.above is not None) else False

            if intersect_above_below:
                bst.above.data.hilight(color_line="yellow",
                                       color_point="yellow")
                bst.below.data.hilight(color_line="yellow",
                                       color_point="yellow")

                return True

            event_point.segment.unhilight()
            bst.delete(event_point.segment)

        control.plot_delete(sweep_line_id)
    return False
Beispiel #38
0
def triang (a, b, c):
	"desenha  (e apaga) os lados do triangulo abc"
	a.lineto (c, config.COLOR_PRIM)
	#b.lineto (a, config.COLOR_PRIM)
	c.lineto (b, config.COLOR_PRIM)
	c.hilight ()
	control.thaw_update ()
	control.update ()
	control.freeze_update ()

	control.sleep ()

	c.unhilight ()
	a.remove_lineto (c)
	#b.remove_lineto (a)
	c.remove_lineto (b)
Beispiel #39
0
def trataCaso3(v,arvore,pontos,vertices,diagonais,faces):
    aux = (arvore.get(v[0])).trap
    arvore.delete(v[0])

    if(pontaParaBaixo(aux[1],pontos)):#aux[1] = vertice de apoio do trapézio
        diagonais.append(Segment(aux[1][0],v[0]))

        aresta = Aresta()
        aresta.setAresta(Segment(aux[1],v))
        aresta2 = Aresta()
        aresta2.setAresta(Segment(v,aux[1]))

        aresta.setGemeo(aresta2)
        aresta2.setGemeo(aresta)

        Segment(aux[1][0],v[0]).hilight("blue")
        control.sleep()
        insereDiagonal(vertices[aux[1][1]-1],vertices[v[1]-1],aresta,faces)
        print "Adicionada diagonal ",Segment(aux[1][0],v[0])
    
    if((aux[0].to.x != v[0].x and aux[0].to.y != v[0].y) or (aux[2].to.x != v[0].x and aux[2].to.y != v[0].y)):#caso tenham 2 trapézios com v
        aux2 = (arvore.get(v[0])).trap #segundo trapézio que contém v
        arvore.delete(v[0])

        if(pontaParaBaixo(aux2[1],pontos)): #aux2[1] = vertice de apoio do segundo trapézio
            diagonais.append(Segment(aux2[1][0],v[0]))

            aresta = Aresta()
            aresta.setAresta(Segment(aux2[1][0],v[0]))
            aresta2 = Aresta()
            aresta2.setAresta(Segment(v[0],aux2[1][0]))

            aresta.setGemeo(aresta2)
            aresta2.SetGemeo(aresta)

            Segment(aux2[1][0],v[0]).hilight("blue")            
            control.sleep()
            insereDiagonal(vertices[aux2[1][1]-1],vertices[v[1]-1],aresta,faces)
            #print "Adicionada diagonal ",Segment(aux2[1][0],v[0])

        if( aux[2].init.x == v[0].x and aux[2].init.y == v[0].y):
            arvore.insert( (aux[0],v,aux2[2]) )
            #print bcolors.OKBLUE,"Inserido trapézio com vértice de apoio ",v," : ",aux[0],aux2[2]
        else:
            arvore.insert( (aux2[0],v,aux[2]) )
Beispiel #40
0
def trataCaso1(u,v,w,arvore,pontos,vertices,diagonais,faces):
    if(u.y < w.y or (u.y == w.y and u.x > w.x ) ): #u <=> w
        aux = w
        w = u 
        u = aux

    aux = (arvore.get(v[0])).trap #aux recebe um trapézio que contem v
    arvore.delete(v[0])
        
    if(v[0].x == aux[0].to.x and v[0].y == aux[0].to.y): 
        arvore.insert((Segment(v[0],w),v,aux[2]))
    else:
        arvore.insert((aux[0],v,Segment(v[0],w)))

    if(pontaParaBaixo(aux[1],pontos)):
        diagonais.append(Segment(aux[1][0],v[0]))

        aresta = criaAresta(aux[1],v)

        Segment(aux[1][0],v[0]).hilight("blue")
        control.sleep()
        insereDiagonal(vertices[aux[1][1]-1],vertices[v[1]-1],aresta,faces)
Beispiel #41
0
def superior_tangent (v, u):
	"""Determina a tangente superior aos poligonos que contem v e u"""
	v.lineto (u, config.COLOR_ALT1)
	hiv = v.hilight ()
	hiu = u.hilight ()

	ch1 = is_sup_tan_ch1 (v, u)
	ch2 = is_sup_tan_ch2 (v, u)
	while not (ch1 and ch2):
		while not ch1:
			v.remove_lineto (u)
			v.unhilight (hiv)

			v = v.next

			hiv = v.hilight ()
			v.lineto (u, config.COLOR_ALT1)
			control.sleep ()
			ch1 = is_sup_tan_ch1 (v, u)

		ch2 = is_sup_tan_ch2 (v, u)
		while not ch2:
			v.remove_lineto (u)
			u.unhilight (hiu)

			u = u.prev

			hiu = u.hilight ()
			v.lineto (u, config.COLOR_ALT1)
			control.sleep ()
			ch2 = is_sup_tan_ch2 (v, u)

		ch1 = is_sup_tan_ch1 (v, u)
	
	v.unhilight (hiv)
	u.unhilight (hiu)
	v.remove_lineto (u)
	return (v, u)
Beispiel #42
0
def trataCaso2(u,v,w,arvore,vertices,diagonais,faces):
    if(left(u,v[0],w )): # u<=>w
        aux = w
        w = u
        u = aux

    aux = arvore.get(v[0])
    arvore.delete(v[0])

    if(aux is None):
        arvore.insert( ( Segment(v[0],u),v,Segment(v[0],w) ) )
    else:
        trap = aux.trap
        arvore.insert( (Segment(v[0],w),v,trap[2]) )  #insiro esse primeiro para respeitar a ordem correta na arvore(dado que eu escolhi comparar por x do vertice de apoio
        arvore.insert( (trap[0],v,Segment(v[0],u)) )

        diagonais.append( Segment(trap[1][0],v[0]) )

        aresta = criaAresta(trap[1],v)
        
        Segment(trap[1][0],v[0]).hilight("blue")
        control.sleep()
        insereDiagonal(vertices[trap[1][1]-1],vertices[v[1]-1],aresta,faces)
Beispiel #43
0
def isEar(n, p, i):
	p[i].hilight('yellow')
	control.sleep ()
	p[(i-1)%n].lineto(p[(i+1)%n], 'yellow')
	control.sleep ()
	ear = isDiagonal(n, p, (i-1)%n, (i+1)%n)
	p[i].unhilight()
	p[(i-1)%n].remove_lineto(p[(i+1)%n])
	if(ear == True):
		p[i].hilight('green')
	control.sleep ()
	return ear
Beispiel #44
0
def lp(l):
    #na arvore, cada trapezio é uma tripla (Segmento,(ponto,indice),Segmento), sendo então trapezio[0] o segmento esquerdo, trapezio[2] o direito e trapezio[1] o vértice de apoio

    arvore = Arvore()

    for x in range(len(l)):
        if(x != len(l)-1): l[x].lineto(l[(x+1)],'red')
        else: l[x].lineto(l[0],'red')                                    
    
    N = len(l)
    pontos = [] #lista de pontos, juntamente com seus indices originais
    verticesOrdenados = [] #lista de pontos ordenada
    diagonais = [] #lista das diagonais que particionam o poligono em poligonos menores monótonos

    for i in range(N): pontos.append((l[i],i))
    verticesOrdenados = sorted(pontos,key=lambda x: (x[0].y,-x[0].x), reverse=True)	 

    verticesDCEL = []
    arestas = []
    arestas2 = []

    ### Essa parte monta a face externa na mão
    for a in range(N):
        if(a != N-1):
            ar = Aresta()
            ar.setAresta(Segment(pontos[a],pontos[a+1]))

            ar2 = Aresta()
            ar2.setAresta(Segment(pontos[a+1],pontos[a]))

            ar.setGemeo(ar2)
            ar2.setGemeo(ar)

            arestas.append(ar)
            arestas2.append(ar2)
            
        else:
            ar = Aresta()
            ar.setAresta(Segment(pontos[a],pontos[0]))

            ar2 = Aresta()
            ar2.setAresta(Segment(pontos[0],pontos[a]))

            ar.setGemeo(ar2)
            ar2.setGemeo(ar)

            arestas.append(ar)
            arestas2.append(ar2)

    for k in range(len(arestas)):
        if(k!= 0 and k!= len(arestas)-1):
            arestas[k].setProx(arestas[k+1])
            arestas[k].setAnt(arestas[k-1])

            arestas2[k].setProx(arestas2[k-1])
            arestas2[k].setAnt(arestas2[k+1])
        elif(k == 0):
            arestas[k].setProx(arestas[k+1])
            arestas[k].setAnt(arestas[len(arestas)-1])

            arestas2[k].setProx(arestas2[len(arestas)-1])
            arestas2[k].setAnt(arestas2[k+1])
        else:
            arestas[k].setProx(arestas[0])
            arestas[k].setAnt(arestas[k-1])

            arestas2[k].setProx(arestas2[k-1])
            arestas2[k].setAnt(arestas2[0])
    ###

    for a in range(N):
        v = Vertice(aresta=arestas2[a])
        verticesDCEL.append(v)          


    face = Face(arestas2[0])
    faces = []

    faces.append(face)

############## Esse pedaço verifica se o poligono passado já é estritamente monotono. Se for ele passa a lista de pontos para o algoritmo de triangulação de monótonos
    monotono = True
    for i in range(1,N-1):
        if(pontaParaBaixo(verticesOrdenados[i],pontos) or pontaParaCima(verticesOrdenados[i],pontos)):
            monotono = False

    if(monotono == True):
        triangulaMonotono(faces[0].listaFace())
        return 0;
################

    for k in range(0,N):
        verticesOrdenados[k][0].hilight("yellow")

        if(verticesOrdenados[k][1] == 0): ant = len(l)-1
        else: ant = verticesOrdenados[k][1]- 1

        if(verticesOrdenados[k][1] == len(l)-1): prox = 0
        else: prox = verticesOrdenados[k][1] + 1

        pontos[ant][0].hilight("cyan")
        pontos[prox][0].hilight("green")
        control.sleep()

        if( (maisEmBaixoQue(pontos[ant][0],verticesOrdenados[k][0]) and maisEmCimaQue(pontos[prox][0],verticesOrdenados[k][0])) or (maisEmBaixoQue(pontos[prox][0],verticesOrdenados[k][0]) and maisEmCimaQue(pontos[ant][0],verticesOrdenados[k][0])) ):#Caso 1: uma aresta acima e outra embaixo
            trataCaso1(pontos[ant][0],verticesOrdenados[k],pontos[prox][0],arvore,pontos,verticesDCEL,diagonais,faces)
        elif(maisEmBaixoQue(pontos[ant][0],verticesOrdenados[k][0])): # Caso 2: as duas arestas abaixo
            trataCaso2(pontos[ant][0],verticesOrdenados[k],pontos[prox][0],arvore,verticesDCEL,diagonais,faces)
        else: #Caso 3: as duas arestas em cima
            trataCaso3(verticesOrdenados[k],arvore,pontos,verticesDCEL,diagonais,faces)

        verticesOrdenados[k][0].hilight("red")
        pontos[ant][0].hilight("red")
        pontos[prox][0].hilight("red")

    
    for f in faces:
        if( f != face ): # se não for a face externa
            triangulaMonotono(f.listaFace())

    for d in diagonais:
        d.hilight('blue')
Beispiel #45
0
def Hull2D (P, m, H):

	#print m, H
	lines = []
	n = len (P)
	CHs = []
	num = n/m

	a = 0
	while a < n:
		b = min (a+m, n)
		l = P[a:b]
		ids = []
		for p in l: ids.append (p.hilight ())
		ch = Graham (l)
		#ch.hide ()
		for p in P[a:b]: p.unhilight (ids.pop ())
		CHs.append (ch)
		a = b

	i0 = 0
	# encontrando o ponto mais a direita
	p0 = CHs[0].pts
	for ch in CHs:
		for p in ch.to_list ():
			if p.x > p0.x: p0 = p
			elif p.x == p0.x: 
				if p.x > p0.x: p0 = p
	
	fecho = [ p0 ]
	for ch in CHs: ch.hide ()
	#control.sleep (2)
	for k in range (0, H):
		Q = []
		for ch in CHs:
			ch.plot ()
			p = ch.pts
			initial = 1
			while 1:
				direction = area2 (fecho[-1], p, p.next)
				if direction < 0:
					p = p.next
					initial = 0
				elif direction == 0 \
					and dist2 (fecho[-1], p) \
					    < dist2 (fecho[-1], p.next):
					p = p.next
					initial = 0
				elif initial:
					p = p.next
				else:
					Q.append (p)
					p.hilight ()
					control.sleep ()
					ch.pts = p.prev
					ch.hide ()
					break
			

		control.sleep ()
		p = Q[0]
		for q in Q[1:]:
			direction = area2 (fecho[-1], p, q)
			if direction < 0:
				p = q
			elif direction == 0:
				if (dist2 (fecho[-1], p) < dist2 (fecho[-1], q)):
					p = q

		for q in Q: q.unhilight ()
		lines.append (fecho[-1].lineto (p, 'green'))
		fecho.append (p)
		if p == p0: 
			#for ch in CHs: ch.hide ()
			#print 'fecho =',`fecho`
			fecho.pop ()
			for i in lines:
				control.plot_delete (i)
			poly = Polygon (fecho)
			poly.plot ()
			return poly
	
	#for ch in CHs: ch.hide ()
	for i in lines:
		control.plot_delete (i)
	return None
Beispiel #46
0
def triangulaMonotono(l):#Os pontos devem vir em ordem anti-horária
    pontos = [] #lista com os pontos,juntamente com seus indices
    verticesOrdenados = [] #lista com os pontos ordenados
    pilha = [] #pilha usada no algoritmo
    #diagonais = [] #lista de diagonais da triangulação
    lado = []

    for x in range(len(l)):#desenha poligono
        if(x != len(l)-1): l[x].lineto(l[(x+1)],'red')
        else: l[x].lineto(l[0],'red')
                                        
    N = len(l)

    for i in range(N): 
        pontos.append((l[i],i)) #transforma cada ponto numa dupla (ponto,indice)
        lado.append(True)
    
    ########################################### 
    verticesOrdenados = merge(pontos,lado)
    ########################################

    pilha.append(verticesOrdenados[0])
    pilha.append(verticesOrdenados[1])

    for i in range(2,N):
        t = len(pilha)
        verticesOrdenados[i][0].hilight("yellow")
        control.sleep()
        if(verticesOrdenados[i][1] == 0): ant = len(l)-1
        else: ant = verticesOrdenados[i][1]-1

        if(verticesOrdenados[i][1] == len(l)-1): prox = 0
        else: prox = verticesOrdenados[i][1]+1

        #aqui pilha[t-1][1] é o St e pilha[0][1] o S1, de acordo com os slides

   #Caso A ########################
        if((ant == pilha[t-1][1] and prox != pilha[0][1]) or (ant != pilha[0][1] and prox == pilha[t-1][1])): #adjacente a St mas nao a S1   
            if(lado[pilha[t-1][1]] == True):   
                while(t>1 and left_on(pilha[t-1][0],pilha[t-2][0],verticesOrdenados[i][0]) and not (pilha[t-1][0].y == pilha[t-2][0].y and verticesOrdenados[i][0].y == pilha[t-1][0].y )):                    
                    pilha.pop()
                    t -= 1
                    d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                    d.hilight("blue")
                    control.sleep()
            elif(t>1):
                while(t>1 and right_on(pilha[t-1][0],pilha[t-2][0],verticesOrdenados[i][0])  and not (pilha[t-1][0].y == pilha[t-2][0].y and verticesOrdenados[i][0].y == pilha[t-1][0].y )):
                    pilha.pop()
                    t -= 1
                    d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                    d.hilight("blue")
                    control.sleep()

                    
            pilha.append(verticesOrdenados[i])

   #Caso B ########################
        if((ant != pilha[t-1][1] and prox == pilha[0][1]) or (ant == pilha[0][1] and prox != pilha[t-1][1])): #adjacente a S1 mas nao a St
            aux = pilha[t-1]
            while(t>1):
                d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                d.hilight("blue")
                control.sleep()
                pilha.pop()
                t -= 1
            pilha.pop()
            pilha.append(aux)
            pilha.append(verticesOrdenados[i])
   #Caso C ########################
        if((ant == pilha[t-1][1] and prox == pilha[0][1]) or (ant == pilha[0][1] and prox == pilha[t-1][1])): #adjacente a St e S1
            pilha.pop()
            while(t>2):
                t -= 1
                d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                d.hilight("blue")
                control.sleep()
                pilha.pop()
        verticesOrdenados[i][0].hilight("red")
Beispiel #47
0
def triangulaMonotono2(l,diagonais):#Os pontos devem vir em ordem anti-horária
    pontos = [] #lista com os pontos,juntamente com seus indices
    verts = [] #lista com os pontos ordenados
    pilha = [] #pilha usada no algoritmo
    lado = []

    for x in range(len(l)):#desenha poligono
        if(x != len(l)-1): l[x].lineto(l[(x+1)],'red')
        else: l[x].lineto(l[0],'red')
                                        
    N = len(l)

    for i in range(N): 
        pontos.append((l[i],i)) #transforma cada ponto numa dupla (ponto,indice)
        lado.append(True)
    
    ########################################### 
    #Esse pedaço acha o vertice mais alto e o mais baixo e realiza o merge
    yMax = -20000000
    yMin = 2000000
    vMax = pontos[0]
    vMin = pontos[N-1]

    for i in range(N):
        if(pontos[i][0].y == yMax and pontos[i][0].x < vMax[0].x): vMax = pontos[i]
        if(pontos[i][0].y == yMin and pontos[i][0].x > vMin[0].x): vMin = pontos[i]
        if(pontos[i][0].y > yMax):
            vMax = pontos[i]
            yMax = vMax[0].y
        if(pontos[i][0].y < yMin):
            vMin = pontos[i]
            yMin = vMin[0].y
            
    if(vMax[1] != N-1):v = pontos[vMax[1]+1]
    else: v = pontos[0]
            
    if(vMax[1]!= 0): i = vMax[1]-1
    else: i = N-1

    if(vMax[1]!= N-1):j = vMax[1]+1
    else: j = 0

    lado[vMin[1]] = False

    if(vMax[1]!= 0): i = vMax[1]-1
    else: i = N-1

    if(vMax[1]!= N-1):j = vMax[1]+1
    else: j = 0            

    verts.append(vMax);
    while(len(verts) < N): #Merge
        if(pontos[j] == vMin):
            while(pontos[i] != vMin):
                verts.append(pontos[i])
                if(i!=0):i -= 1
                else: i = N-1
        elif(pontos[i] == vMin):
            while(pontos[j] != vMin):
                lado[pontos[j][1]] = False
                verts.append(pontos[j])
                if(j != N-1):j += 1
                else: j = 0

        if((pontos[j][0].y >= pontos[i][0].y)):
            lado[pontos[j][1]] = False
            verts.append(pontos[j])
            if(j != N-1): j+= 1
            else: j = 0
        else:
            verts.append(pontos[i])
            if(i!=0):i -= 1
            else: i = N-1

    ########################################

    #verts = sorted(pontos,key=lambda x: (x[0].y,-x[0].x), reverse=True)	 

    print verts

    pilha.append(verts[0])
    pilha.append(verts[1])

    for i in range(2,N):
        t = len(pilha)
        print "____________________"
        print pilha
        verts[i][0].hilight("yellow")
        control.sleep()
        if(verts[i][1] == 0): ant = len(l)-1
        else: ant = verts[i][1]-1

        if(verts[i][1] == len(l)-1): prox = 0
        else: prox = verts[i][1]+1

        #aqui pilha[t-1][1] é o St e pilha[0][1] o S1, de acordo com os slides

   #Caso A ########################
        if((ant == pilha[t-1][1] and prox != pilha[0][1]) or (ant != pilha[0][1] and prox == pilha[t-1][1])): #adjacente a St mas nao a S1   
            print "Entrei no caso A" , "no vertice ",verts[i][0]
            if(lado[pilha[t-1][1]] == True):   
                while(t>1 and left_on(pilha[t-1][0],pilha[t-2][0],verts[i][0]) ):                
                    pilha.pop()
                    t -= 1
                    diagonais.append(Segment(verts[i][0],pilha[t-1][0]))
                    d = Segment(verts[i][0],pilha[t-1][0])
                    d.hilight("blue")
                    control.sleep()
                    print "Adicionei a diagonal ", d
            elif(t>1):
                while(t>1 and right_on(pilha[t-1][0],pilha[t-2][0],verts[i][0])):
                    
                    pilha.pop()
                    t -= 1
                    diagonais.append(Segment(verts[i][0],pilha[t-1][0]))
                    d = Segment(verts[i][0],pilha[t-1][0])
                    d.hilight("blue")
                    control.sleep()
                    print "Adicionei a diagonal ", d
                    
            pilha.append(verts[i])

   #Caso B ########################
        if((ant != pilha[t-1][1] and prox == pilha[0][1]) or (ant == pilha[0][1] and prox != pilha[t-1][1])): #adjacente a S1 mas nao a St
            print "Entrei no caso B"  , "no vertice ",verts[i][0]
            aux = pilha[t-1]
            while(t>1):
                diagonais.append(Segment(verts[i][0],pilha[t-1][0]))
                d = Segment(verts[i][0],pilha[t-1][0])
                d.hilight("blue")
                control.sleep()
                print "Adicionei a diagonal ", d
                pilha.pop()
                t -= 1
            pilha.pop()
            pilha.append(aux)
            pilha.append(verts[i])
   #Caso C ########################
        if((ant == pilha[t-1][1] and prox == pilha[0][1]) or (ant == pilha[0][1] and prox == pilha[t-1][1])): #adjacente a St e S1
            print "Entrei no caso C", "no vertice ",verts[i][0]
            pilha.pop()
            while(t>2):
                t -= 1
                diagonais.append(Segment(verts[i][0],pilha[t-1][0]))
                d = Segment(verts[i][0],pilha[t-1][0])
                d.hilight("blue")
                control.sleep()
                print "Adicionei a diagonal ", d
                pilha.pop()
        verts[i][0].hilight("red")
        print "--------------------"

    return diagonais
def blink (p, q):
	p.hilight ()
	q.hilight ()
	control.sleep ()
	p.unhilight ()
	q.unhilight ()
Beispiel #49
0
def triangulaMonotono(l):#Os pontos devem vir em ordem anti-horária
    pontos = [] #lista com os pontos,juntamente com seus indices
    verticesOrdenados = [] #lista com os pontos ordenados
    pilha = [] #pilha usada no algoritmo
    diagonais = [] #lista de diagonais da triangulação
    lado = []

    for x in range(len(l)):#desenha poligono
        if(x != len(l)-1): l[x].lineto(l[(x+1)],'red')
        else: l[x].lineto(l[0],'red')
                                        
    N = len(l)

    for i in range(N): 
        pontos.append((l[i],i)) #transforma cada ponto numa dupla (ponto,indice)
        lado.append(True)

#####################################

    verticesDCEL = []
    arestas = []
    arestas2 = []

    for a in range(N):
        if(a != N-1):
            ar = Aresta()
            ar.setAresta(Segment(pontos[a],pontos[a+1]))

            ar2 = Aresta()
            ar2.setAresta(Segment(pontos[a+1],pontos[a]))

            ar.setGemeo(ar2)
            ar2.setGemeo(ar)

            arestas.append(ar)
            arestas2.append(ar2)
            
        else:
            ar = Aresta()
            ar.setAresta(Segment(pontos[a],pontos[0]))

            ar2 = Aresta()
            ar2.setAresta(Segment(pontos[0],pontos[a]))

            ar.setGemeo(ar2)
            ar2.setGemeo(ar)

            arestas.append(ar)
            arestas2.append(ar2)

    for k in range(len(arestas)):
        if(k!= 0 and k!= len(arestas)-1):
            arestas[k].setProx(arestas[k+1])
            arestas[k].setAnt(arestas[k-1])

            arestas2[k].setProx(arestas2[k-1])
            arestas2[k].setAnt(arestas2[k+1])
        elif(k == 0):
            arestas[k].setProx(arestas[k+1])
            arestas[k].setAnt(arestas[len(arestas)-1])

            arestas2[k].setProx(arestas2[len(arestas)-1])
            arestas2[k].setAnt(arestas2[k+1])
        else:
            arestas[k].setProx(arestas[0])
            arestas[k].setAnt(arestas[k-1])

            arestas2[k].setProx(arestas2[k-1])
            arestas2[k].setAnt(arestas2[0])

    for a in range(N):
        bla = Vertice(aresta=arestas2[a])
        verticesDCEL.append(bla)          


    face = Face(arestas2[0])
    faces = []

    faces.append(face)



######################################
    verticesOrdenados = merge(pontos,lado)
######################################
    
    pilha.append(verticesOrdenados[0])
    pilha.append(verticesOrdenados[1])

    for i in range(2,N):
        t = len(pilha)
        verticesOrdenados[i][0].hilight("yellow")
        control.sleep()
        if(verticesOrdenados[i][1] == 0): ant = len(l)-1
        else: ant = verticesOrdenados[i][1]-1

        if(verticesOrdenados[i][1] == len(l)-1): prox = 0
        else: prox = verticesOrdenados[i][1]+1

        #aqui pilha[t-1][1] é o St e pilha[0][1] o S1, de acordo com os slides

   #Caso A ########################
        if((ant == pilha[t-1][1] and prox != pilha[0][1]) or (ant != pilha[0][1] and prox == pilha[t-1][1])): #adjacente a St mas nao a S1   
            if(lado[pilha[t-1][1]] == True):   
                while(t>1 and left_on(pilha[t-1][0],pilha[t-2][0],verticesOrdenados[i][0]) and not (pilha[t-1][0].y == pilha[t-2][0].y and verticesOrdenados[i][0].y == pilha[t-1][0].y )):                    
                    pilha.pop()
                    t -= 1
                    d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                    d.hilight("green")
                    control.sleep()
                    diagonalASerInserida = criaAresta(verticesOrdenados[i],pilha[t-1])
                    diagonais.append(diagonalASerInserida)
                    insere(verticesDCEL[verticesOrdenados[i][1]-1],verticesDCEL[pilha[t-1][1]-1],diagonalASerInserida,faces)
            elif(t>1):
                while(t>1 and right_on(pilha[t-1][0],pilha[t-2][0],verticesOrdenados[i][0])  and not (pilha[t-1][0].y == pilha[t-2][0].y and verticesOrdenados[i][0].y == pilha[t-1][0].y )):
                    pilha.pop()
                    t -= 1
                    d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                    d.hilight("green")
                    control.sleep()
                    diagonalASerInserida = criaAresta(verticesOrdenados[i],pilha[t-1])
                    diagonais.append(diagonalASerInserida)
                    insere(verticesDCEL[verticesOrdenados[i][1]-1],verticesDCEL[pilha[t-1][1]-1],diagonalASerInserida,faces)

                    
            pilha.append(verticesOrdenados[i])

   #Caso B ########################
        if((ant != pilha[t-1][1] and prox == pilha[0][1]) or (ant == pilha[0][1] and prox != pilha[t-1][1])): #adjacente a S1 mas nao a St
            aux = pilha[t-1]
            while(t>1):
                d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                d.hilight("green")
                control.sleep()
                diagonalASerInserida = criaAresta(verticesOrdenados[i],pilha[t-1])
                diagonais.append(diagonalASerInserida)
                insere(verticesDCEL[verticesOrdenados[i][1]-1],verticesDCEL[pilha[t-1][1]-1],diagonalASerInserida,faces)
                pilha.pop()
                t -= 1
            pilha.pop()
            pilha.append(aux)
            pilha.append(verticesOrdenados[i])
   #Caso C ########################
        if((ant == pilha[t-1][1] and prox == pilha[0][1]) or (ant == pilha[0][1] and prox == pilha[t-1][1])): #adjacente a St e S1
            pilha.pop()
            while(t>2):
                t -= 1
                d = Segment(verticesOrdenados[i][0],pilha[t-1][0])
                d.hilight("green")
                control.sleep()
                diagonalASerInserida = criaAresta(verticesOrdenados[i],pilha[t-1])
                diagonais.append(diagonalASerInserida)
                insere(verticesDCEL[verticesOrdenados[i][1]-1],verticesDCEL[pilha[t-1][1]-1],diagonalASerInserida,faces)
                pilha.pop()
        verticesOrdenados[i][0].hilight("red")
        
    for d in diagonais:
        checaDiagonal(verticesDCEL[d.getAresta().init[1] -1 ],verticesDCEL[d.getAresta().to[1] -1 ],d)
Beispiel #50
0
def LeePreparata(p):
	print ""
	if(len(p) <= 3):
		return 0
	PlotPolygon(p)
	n = len(p)
	t = avl()
	d = dcel()
	d.createDCELfromPolygon(p)
	od = orderedDCEL(d, p[0], n)
	event = MergeSort(p, range(0, n))


	for i in range(0, n):


		p[event[i]].hilight('yellow')

		# Caso 2 - Ponta para cima
		if(upSpike(p, event[i])):
			node = t.findNode(p[event[i]])
			# Caso nao haja trapezio em cima de do ponto evento
			if(node == None):
				left = leftEdge(p, event[i], n)
				trap = trapezoid(p[event[i]], event[i], p[event[i]], p[(event[i]+left)%n], p[event[i]], p[(event[i]-left)%n])
				t.insert(trap)
				control.sleep ()
			# Caso haja um trapezio em cima do ponto evento
			else:
				node.value.leo.lineto(node.value.led, 'green')
				node.value.reo.lineto(node.value.red, 'green')
				node.value.top.hilight('green')
				control.sleep ()
				left = leftEdge(p, event[i], n)
				trap1 = trapezoid(p[event[i]], event[i], node.value.leo, node.value.led, p[event[i]], p[(event[i]+left)%n])
				trap2 = trapezoid(p[event[i]], event[i], p[event[i]], p[(event[i]-left)%n], node.value.reo, node.value.red)
				insertEdgeUsingOd(od, d, event[i], node)
				print str(od[event[i]][0].origin)+str(od[node.value.topIndex][0].origin)
				od[event[i]][0].origin.lineto(od[node.value.topIndex][0].origin, 'red')
				control.sleep ()
				node.value.leo.remove_lineto(node.value.led)
				node.value.reo.remove_lineto(node.value.red)
				node.value.top.unhilight()
				t.remove(p[event[i]])
				t.insert(trap2)
				t.insert(trap1)


		# Caso 3 - Ponta para baixo
		elif(downSpike(p, event[i])):
			node = t.findNode(p[event[i]])
			suc = t.sucessor(node)
			pred = t.predecessor(node)
			node.value.leo.lineto(node.value.led, 'green')
			node.value.reo.lineto(node.value.red, 'green')
			node.value.top.hilight('green')
			# Caso haja dois trapezios em cima do ponto evento
			if(suc != None and suc.value.equal(p[event[i]])):
				suc.value.leo.lineto(suc.value.led, 'cyan')
				suc.value.reo.lineto(suc.value.red, 'cyan')
				suc.value.top.hilight('cyan')
				control.sleep ()
				trap = trapezoid(p[event[i]], event[i], node.value.leo, node.value.led, suc.value.reo, suc.value.red)
				if(downSpike(p, node.value.topIndex) and abs(event[i]-node.value.topIndex) > 1):
					insertEdgeUsingOd(od, d, event[i], node)
					print str(od[event[i]][0].origin)+str(od[node.value.topIndex][0].origin)
					od[event[i]][0].origin.lineto(od[node.value.topIndex][0].origin, 'red')
				if(downSpike(p, suc.value.topIndex) and abs(event[i]-suc.value.topIndex) > 1):
					insertEdgeUsingOd(od, d, event[i], suc)
					print str(od[event[i]][0].origin)+str(od[suc.value.topIndex][0].origin)	
					od[event[i]][0].origin.lineto(od[suc.value.topIndex][0].origin, 'red')
				control.sleep ()
				node.value.leo.remove_lineto(node.value.led)
				node.value.reo.remove_lineto(node.value.red)
				node.value.top.unhilight()
				suc.value.leo.remove_lineto(suc.value.led)
				suc.value.reo.remove_lineto(suc.value.red)
				suc.value.top.unhilight()
				t.remove(p[event[i]])
				t.remove(p[event[i]])
				t.insert(trap)
				control.sleep ()
			elif(pred != None and pred.value.equal(p[event[i]])):
				pred.value.leo.lineto(pred.value.led, 'cyan')
				pred.value.reo.lineto(pred.value.red, 'cyan')
				pred.value.top.hilight('cyan')
				control.sleep ()
				trap = trapezoid(p[event[i]], event[i], pred.value.leo, pred.value.led, node.value.reo, node.value.red)
				if(downSpike(p, node.value.topIndex) and abs(event[i]-node.value.topIndex) > 1):
					insertEdgeUsingOd(od, d, event[i], node)
					print str(od[event[i]][0].origin)+str(od[node.value.topIndex][0].origin)
					od[event[i]][0].origin.lineto(od[node.value.topIndex][0].origin, 'red')
				if(downSpike(p, pred.value.topIndex) and abs(event[i]-pred.value.topIndex) > 1):
					insertEdgeUsingOd(od, d, event[i], pred)
					print str(od[event[i]][0].origin)+str(od[pred.value.topIndex][0].origin)
					od[event[i]][0].origin.lineto(od[pred.value.topIndex][0].origin, 'red')
				control.sleep ()
				node.value.leo.remove_lineto(node.value.led)
				node.value.reo.remove_lineto(node.value.red)
				node.value.top.unhilight()
				pred.value.leo.remove_lineto(pred.value.led)
				pred.value.reo.remove_lineto(pred.value.red)
				pred.value.top.unhilight()
				t.remove(p[event[i]])
				t.remove(p[event[i]])
				t.insert(trap)
				control.sleep ()

			# Caso so haja um trapezio em cima do ponto evento
			else:
				if(downSpike(p, node.value.topIndex) and abs(event[i]-node.value.topIndex) > 1):
					insertEdgeUsingOd(od, d, event[i], node)
					print str(od[event[i]][0].origin)+str(od[node.value.topIndex][0].origin)
					od[event[i]][0].origin.lineto(od[node.value.topIndex][0].origin, 'red')
				control.sleep ()
				node.value.leo.remove_lineto(node.value.led)
				node.value.reo.remove_lineto(node.value.red)
				node.value.top.unhilight()
				t.remove(p[event[i]])
				control.sleep ()

		
		# Caso 1 - Uma aresta para cima e outra para baixo			
		else:
			node = t.findNode(p[event[i]])
			node.value.leo.lineto(node.value.led, 'green')
			node.value.reo.lineto(node.value.red, 'green')
			node.value.top.hilight('green')
			if(collinear(node.value.leo, node.value.led, p[event[i]])):
				trap = trapezoid(p[event[i]], event[i], p[event[i]], p[(event[i]+downEdge(p, event[i], n))%n], node.value.reo, node.value.red)
			else:
				trap = trapezoid(p[event[i]], event[i], node.value.leo, node.value.led, p[event[i]], p[(event[i]+downEdge(p, event[i], n))%n])
			if(downSpike(p, node.value.topIndex) and abs(event[i]-node.value.topIndex) > 1):
					insertEdgeUsingOd(od, d, event[i], node)
					print str(od[event[i]][0].origin)+str(od[node.value.topIndex][0].origin)
					od[event[i]][0].origin.lineto(od[node.value.topIndex][0].origin, 'red')
			control.sleep ()
			node.value.leo.remove_lineto(node.value.led)
			node.value.reo.remove_lineto(node.value.red)
			node.value.top.unhilight()
			t.remove(p[event[i]])
			t.insert(trap)
			control.sleep ()

		p[event[i]].unhilight()
		control.sleep ()

	TriangMonotoneUsingDCEL(d)
	return 0
Beispiel #51
0
def IncrProb (l):
	"Algoritmo incremental probabilistico para encontrar o fecho convexo"

	if len (l) == 0: return None

	# Embaralhando o vetor de entrada
	for i in range (len (l) -1, -1, -1):
		index = int (random.uniform (0, i+1))
		aux = l[i]
		l[i] = l[index]
		l[index] = aux
	
	# Inicializando alguns campos...
	for i in range (0, len(l)):
		l[i].L = []
		l[i].interior = 0
		

	# Criando um fecho convexo com 1 ponto
	fecho = Polygon ([ l[0] ])
	fecho.plot ()
	
	length = 1
	k = 0
	hi = l[k].hilight ()
	# Como nao posso admitir que os pontos estao em posicao geral,
	#  preciso tomar cuidado ate' conseguir um fecho convexo com
	#  3 pontos
	for k in range (1, len (l)):
		pts = fecho.pts
		l[k-1].unhilight (hi)
		hi = l[k].hilight ()
		control.thaw_update ()
		if length == 1:
			if l[k].x == pts.x and l[k].y == pts.y:
				continue
			fecho.hide ()
			pts.next = pts.prev = l[k]
			l[k].next = l[k].prev = pts
			fecho.pts = pts
			fecho.plot ()
			length = length + 1
		
		elif length == 2:
			next = pts.next
			dir = area2 (pts, next, l[k])
			if dir == 0:
				#Mais um ponto colinear -> pega o par mais distante
				fecho.hide ()
				dist_pts_next = dist2 (pts, next)
				dist_pts_lk = dist2 (pts, l[k])
				dist_next_lk = dist2 (next, l[k])
				if dist_pts_next >= dist_pts_lk and dist_pts_next >= dist_next_lk:
					a = pts
					b = next
				elif dist_pts_lk >= dist_pts_next  and  dist_pts_lk >= dist_next_lk:
					a = pts
					b = l[k]
				elif dist_next_lk >= dist_pts_lk and dist_next_lk >= dist_pts_next:
					a = next
					b = l[k]
				else:
					print('pau!!!')

				a.next = a.prev = b
				b.next = b.prev = a
				fecho.pts = a
				fecho.plot ()

				continue
			fecho.hide ()
			# Um ponto /nao/ colinear :) -> tomar cuidado com a 
			#  orientacao
			if dir > 0:
				pts.prev = next.next = l[k]
				l[k].next = pts
				l[k].prev = next
			else:
				pts.next = next.prev = l[k]
				l[k].prev = pts
				l[k].next = next

			length = length + 1
			fecho.pts = pts
			fecho.plot ()
			O = classify (fecho, l, k)
			break

	# Ja temos um fecho com 3 pontos -> basta cresce-lo
	for k in range (k+1, len (l)):
		pts = fecho.pts
		l[k-1].unhilight (hi)
		hi = l[k].hilight ()
		control.thaw_update ()

		if l[k].interior:
			control.sleep ()
			continue

		l[k].remove_lineto (l[k].intersect)
		control.sleep ()

		tan = vertices_tangentes (l[k].intersect, l[k])

		l[k].intersect.L.remove (l[k])

		l0 = []
		l1 = []
		# atualizando a classificacao dos pontos
		vertex = tan[0]
		while vertex != tan[1]:
			for p in vertex.L:
				id = p.hilight (config.COLOR_ALT3)
				p.remove_lineto (p.intersect)

				if p == l[k]:
					p.unhilight (id)
					continue

				if left (l[k], O, p):
					if left_on (tan[0], l[k], p):
						p.interior = 1
						p.intersect = None
					else:
						p.intersect = tan[0]
						p.lineto (p.intersect, config.COLOR_ALT1)
						l0.append (p)
				else:
					if left_on (l[k], tan[1], p):
						p.interior = 1
						p.intersect = None
					else:
						p.intersect = l[k]
						p.lineto (p.intersect, config.COLOR_ALT1)
						l1.append (p)

				p.unhilight (id)

			vertex = vertex.next

		tan[0].L = l0
		l[k].L = l1

		# atualizando o fecho
		control.freeze_update ()
		fecho.hide ()

		tan[0].next.prev = None
		tan[0].next = l[k]
		l[k].prev = tan[0]

		if tan[1].prev: tan[1].prev.next = None
		tan[1].prev = l[k]
		l[k].next = tan[1]

		fecho.pts = tan[0]
		fecho.plot ()

		control.thaw_update ()

	l[k].unhilight (hi)
	fecho.plot ()
	fecho.extra_info = 'vertices: %d'%len (fecho.to_list ())
	return fecho
Beispiel #52
0
def TriangMonotoneUsingDCEL(d):
    for f in range(1, len(d.faces)):

        if d.faces[f].verified == False:

            event = generateDecreasingVerticeList(d, f)
            s = stack()

            s1 = event[0]
            s.insert(event[0])
            s.insert(event[1])

            s1.origin.hilight("cyan")

            for i in range(2, len(event)):
                st = s.getTop()
                staux = s.getTop().origin
                staux.hilight("green")
                aux = event[i].origin
                aux.hilight("yellow")
                control.sleep()

                if not Adjacent(event[i], s1) and Adjacent(event[i], st):
                    while s.size > 1 and not Reflex(event[i], st, s.getSecond()):
                        s.remove()
                        st = s.getTop()
                        print (str(event[i].origin) + " " + str(st.origin))
                        event[i].origin.lineto(st.origin, "red")
                        control.sleep()

                    s.insert(event[i])
                    staux.unhilight()

                elif Adjacent(event[i], s1) and not Adjacent(event[i], st):
                    while s.size > 1:
                        print (str(event[i].origin) + " " + str(s.getTop().origin))
                        event[i].origin.lineto(s.getTop().origin, "red")
                        control.sleep()
                        s.remove()
                    s.remove()
                    s.insert(st)
                    s.insert(event[i])
                    s1.origin.unhilight()
                    s1 = st
                    staux.unhilight()
                    control.sleep()
                    s1.origin.hilight("cyan")

                elif Adjacent(event[i], s1) and Adjacent(event[i], st):
                    s.remove()
                    while s.size > 1:
                        print (str(event[i].origin) + " " + str(s.getTop().origin))
                        event[i].origin.lineto(s.getTop().origin, "red")
                        control.sleep()
                        s.remove()
                    s1.origin.unhilight()
                    staux.unhilight()

                else:
                    print "wtf"
                aux.unhilight()

                control.sleep()

    return 0
Beispiel #53
0
def bhatta_sen_upper_rec (a, b, S):
	"""Constroi a parte superior do fecho convexo"""
	
	# step 1/2/3
	again = 1

	while again:
		if len (S) == 1:
			return [ S[0] ]
		j = int (random.uniform (0, len (S)/2))
		again = 0

		p1 = S[2*j+1]
		p2 = S[2*j]
		p1.hilight ()
		p2.hilight ()
		if inside_restricted (b, a, S[2*j+1], S[2*j]):
			S.remove (S[2*j])
			again = 1
		elif inside_restricted (b, a, S[2*j], S[2*j+1]):
			S.remove (S[2*j+1])
			again = 1

		p1.unhilight ()
		p2.unhilight ()

	
	# step 4
	m = 0
	if left (S[2*j], S[2*j+1], a):
		p1 = S[2*j+1]
		p2 = S[2*j]
	else:
		p1 = S[2*j]
		p2 = S[2*j+1]
	id = p1.lineto (p2, config.COLOR_ALT4)
	area_m = area2 (p1, p2, S[m])
	for i in range (1, len(S)):
		area_i = area2 (p1, p2, S[i])
		if area_i > area_m:
			m = i
			area_m = area_i
	pm = S[m]
	control.plot_delete (id)

	id = pm.hilight (config.COLOR_ALT1)
	control.sleep ()
	
	S1 = []
	S2 = []

	# step 5
	i = j
	#map (lambda p: p.hilight (config.COLOR_ALT2), S)
	#control.sleep ()
	#map (lambda p: p.unhilight (), S)
	control.sleep ()
	cont = []
	for j in range (0, len(S)/2):
		cont.extend ([2*j, 2*j+1])
		if S[2*j].x < S[2*j+1].x:
			p1 = S[2*j]
			p2 = S[2*j+1]
		else:
			p1 = S[2*j+1]
			p2 = S[2*j]

		p1.hilight ()
		p2.hilight (config.COLOR_ALT3)

		if p2.x <= pm.x:
			if left (pm, p2, p1):
				S1.append (p1)
				S1.append (p2)
			else:
				S1.append (p1)
		elif pm.x <= p1.x:
			if left (pm, p1, p2):
				S2.append (p2)
			else:
				S2.append (p1)
				S2.append (p2)
		else: # p1.x < pm.x < p2.x
			control.sleep ()
			S1.append (p1)
			S2.append (p2)

		p1.unhilight ()
		p2.unhilight ()

	pm.unhilight (id)
	if len (S) % 2 == 1:
		S1.append (S[-1])
		S2.append (S[-1])
	control.sleep ()
	
	map (lambda p: p.hilight (), S1)
	control.sleep ()
	
	# step 6
	for p in S1[:]:
		if not left (b, pm, p):
			S1.remove (p)
			p.unhilight ()

	control.sleep ()
	map (lambda p: p.unhilight (), S1)
	control.sleep ()
	map (lambda p: p.hilight (), S2)
	control.sleep ()

	for p in S2[:]:
		if not left (pm, a, p):
			S2.remove (p)
			p.unhilight ()
	control.sleep ()
	map (lambda p: p.unhilight (), S2)

	# step 7
	ret1 = []
	ret2 = []
	if len (S2) != 0:
		id = a.lineto (pm, config.COLOR_ALT4)
		ret2 = bhatta_sen_upper_rec (a, pm, S2)
		a.remove_lineto (pm, id)
		ret2[-1].lineto (pm)
	ret2.append (pm)
	if len (S1) != 0:
		id = pm.lineto (b, config.COLOR_ALT4)
		ret1 = bhatta_sen_upper_rec (pm, b, S1) 
		pm.remove_lineto (b, id)
		pm.lineto (ret1[0])
	
	ret2.extend (ret1)

	return ret2
def shamos_hoey(segmentos, estrutura):
    global cores

    if len(segmentos) == 0: return None

    # Abaixo, redefinimos as funcoes de comparacao de segmentos para nosso proposito
    Segment.__lt__ = lambda s1, s2: prim.compara_segmentos(x_linha_varredura, s1, s2) == -1
    Segment.__ge__ = lambda s1, s2: prim.compara_segmentos(x_linha_varredura, s1, s2) >= 0

    E = [] # inicializa fila de eventos

    for i, segmento in enumerate(segmentos):
        # se e_x > d_x, entao inverte os pontos que determinam o segmento 
        # (pontos da esquerda nao podem ter x-coordenada maior que pontos da direita)
        if (segmento.init.x > segmento.to.x): 
            segmento.reverse()

        # tambem inverte se for segmento vertical com inicio (init) com menor y-coordenada do que fim (to)
        elif (segmento.init.x == segmento.to.x and segmento.init.y < segmento.to.y):
            segmento.reverse()

        segmento.id = i
        segmento.intersected = False
        # coloca na fila de eventos E
        E.append(PontoEvento(segmento.init, 'esquerdo', i))
        E.append(PontoEvento(segmento.to, 'direito', i))

    E.sort() # ordena pontos eventos por x-coordenada

    global x_linha_varredura

    pred,suc = None, None

    for ponto_evento in E:
        x_linha_varredura = ponto_evento.ponto.x

        #Remove o destaque da iteracao passada
        destaca_segs( [pred, suc], 'presente')

        seg = segmentos[ponto_evento.id_segmento]
        pred = estrutura.predecessor(seg)
        suc = estrutura.sucessor(seg)

        #Destaca os segmentos que serao analisados
        destaca_segs( [pred, suc], 'vizinho')

        if ponto_evento.tipo == 'esquerdo':
            destaca_segs([seg], 'presente')
            estrutura.insere(seg)
            if pred != None:
                if prim.inter(seg,pred) == True: # Detectou interseccao do seg com o pred
                    destaca_segs([seg,pred], 'intersectado')
                    seg.intersected, pred.intersected = True, True
                    break

            if suc != None:
                if prim.inter(seg,suc) == True: # Detectou interseccao do seg com o suc
                    destaca_segs([seg,suc], 'intersectado')
                    seg.intersected, suc.intersected = True, True
                    break

        elif ponto_evento.tipo == 'direito':
            destaca_segs([seg], 'passado')
            estrutura.remove(seg)
            if (pred != None and suc != None):
                if prim.inter(pred,suc) == True: # Detectou interseccao do pred com o suc
                    destaca_segs([pred,suc], 'intersectado')
                    pred.intersected, suc.intersected = True, True
                    break

        linha_varredura_plotada_id = control.gui.plot_vert_line (x_linha_varredura, config.COLOR_LINE_SPECIAL, 1) # plota a linha de varredura
        control.sleep() # dorme
        control.gui.plot_delete(linha_varredura_plotada_id) # desplota a linha de varredura

    if estrutura.__class__.__name__ == 'Skiplist':
        ret = Segment() # pequeno hack, porque resolvemos um problema de decisão, e não temos nada (nenhum polígono, por exemplo) para retornar
                        # e para o algoritmo de Skip List queremos devolver essa informacao extra abaixo
        ret.extra_info = 'SL: p = ' + str(estrutura.p) + ' nivelmax = '  + str(estrutura.maxnivel) + ' (media de niveis = ' + str( (estrutura.somaniveis / (2*len(segmentos)))) + ')'
        return ret
Beispiel #55
0
def Brute(p):
	print ""
	if(len(p) <= 3):
		return 0
	PlotPolygon(p)
	n = len(p)
	ear = findAllEars(n, p)
	while(n > 3):
		i = 0
		while ( not ear[i] ):
			i = i+1
		aux = p[i]
		p[i].unhilight()
		p[i].hilight('cyan')
		control.sleep ()
		if(ear[(i-1)%n]):
			p[(i-1)%n].unhilight()
		if(ear[(i+1)%n]):
			p[(i+1)%n].unhilight()
		p[(i-1)%n].lineto(p[(i+1)%n], 'red')
		control.sleep ()
		control.sleep ()
		v2 = p[i]
		v1 = p[(i-1)%n]
		v3 = p[(i+1)%n]
		p.pop(i)
		ear.pop(i)
		n = n - 1
		indv1 = (i-1)%n
		indv3 = i%n
		ear[indv1] = isEar(n, p, indv1)
		control.sleep ()
		ear[indv3] = isEar(n, p, indv3)
		control.sleep ()
		aux.unhilight()
		control.sleep()
		print(str(v1)+" "+str(v3))
	for i in range(0, 3):
		if(ear[i] == True):
			p[i].unhilight()
	return 0;
Beispiel #56
0
 def __update(self):
     control.thaw_update()
     control.update()
     control.freeze_update()
     control.sleep()
Beispiel #57
0
def lp2(l):
    #na arvore, cada trapezio é uma tripla (Segmento,(ponto,indice),Segmento), sendo então trapezio[0] o segmento esquerdo, trapezio[2] o direito e trapezio[1] o vértice de apoio

    arvore = Arvore()

    for x in range(len(l)):
        if(x != len(l)-1): l[x].lineto(l[(x+1)],'red')
        else: l[x].lineto(l[0],'red')                                    
    
    N = len(l)
    pontos = [] #lista de pontos, juntamente com seus indices originais
    verts = [] #lista de pontos ordenada
    diagonais = [] #lista das diagonais que particionam o poligono em poligonos menores monótonos

    for i in range(N): pontos.append((l[i],i))
    verts = sorted(pontos,key=lambda x: (x[0].y,-x[0].x), reverse=True)	 

    aux = []
    arestas = []
    arestas2 = []

    for a in range(N):
        if(a != N-1):
            ar = Aresta()
            ar.setAresta(Segment(pontos[a],pontos[a+1]))

            ar2 = Aresta()
            ar2.setAresta(Segment(pontos[a+1],pontos[a]))

            ar.setGemeo(ar2)
            ar2.setGemeo(ar)

            arestas.append(ar)
            arestas2.append(ar2)
            
        else:
            ar = Aresta()
            ar.setAresta(Segment(pontos[a],pontos[0]))

            ar2 = Aresta()
            ar2.setAresta(Segment(pontos[0],pontos[a]))

            ar.setGemeo(ar2)
            ar2.setGemeo(ar)

            arestas.append(ar)
            arestas2.append(ar2)

    for k in range(len(arestas)):
        if(k!= 0 and k!= len(arestas)-1):
            arestas[k].setProx(arestas[k+1])
            arestas[k].setAnt(arestas[k-1])

            arestas2[k].setProx(arestas2[k-1])
            arestas2[k].setAnt(arestas2[k+1])
        elif(k == 0):
            arestas[k].setProx(arestas[k+1])
            arestas[k].setAnt(arestas[len(arestas)-1])

            arestas2[k].setProx(arestas2[len(arestas)-1])
            arestas2[k].setAnt(arestas2[k+1])
        else:
            arestas[k].setProx(arestas[0])
            arestas[k].setAnt(arestas[k-1])

            arestas2[k].setProx(arestas2[k-1])
            arestas2[k].setAnt(arestas2[0])

    for a in range(N):
        bla = Vertice(aresta=arestas2[a])
        aux.append(bla)          
        
    face = Face(arestas2[0])
    faces = []

    faces.append(face)

############## Esse pedaço verifica se o poligono passado já é monotono. Se for ele passa a lista de pontos para o algoritmo de triangulação de monótonos

    #monotono = True
    #for i in range(1,N-1):
    #    if(pontaParaBaixo(verts[i],pontos) or pontaParaCima(verts[i],pontos)):
    #        monotono = False

    #if(monotono == True):
    #    triangulaMonotono(faces[0].listaFace())
    #    return 0;
################

    for k in range(0,N):
        verts[k][0].hilight("yellow")

        if(verts[k][1] == 0): ant = len(l)-1
        else: ant = verts[k][1]-1

        if(verts[k][1] == len(l)-1): prox = 0
        else: prox = verts[k][1] +1

        pontos[ant][0].hilight("blue")
        pontos[prox][0].hilight("green")
        control.sleep()

        if( (pontos[ant][0].y <= verts[k][0].y and verts[k][0].y < pontos[prox][0].y) or (pontos[prox][0].y <= verts[k][0].y and verts[k][0].y < pontos[ant][0].y) ): #Caso 1: uma aresta acima e outra embaixo
            print "ENTREI NO CASO 1 NO VÉRTICE ", verts[k][0]
            trataCaso1(pontos[ant][0],verts[k],pontos[prox][0],arvore,pontos,aux,diagonais,faces)
        elif(pontos[ant][0].y <= verts[k][0].y): #Caso 2: as duas arestas embaixo
            print "ENTREI NO CASO 2 NO VÉRTICE ",verts[k][0]
            trataCaso2(pontos[ant][0],verts[k],pontos[prox][0],arvore,aux,diagonais,faces)
        else: #Caso 3: as duas arestas em cima
            print "ENTREI NO CASO 3 NO VÉRTICE ", verts[k][0]
            trataCaso3(verts[k],arvore,pontos,aux,diagonais,faces)

        verts[k][0].hilight("red")
        pontos[ant][0].hilight("red")
        pontos[prox][0].hilight("red")


    for bla in faces:
        if( bla != face ):
            triangulaMonotono2(bla.listaFace(),diagonais)

    for d in diagonais:
        d.hilight('blue')

    return diagonais
def Diameter (l):
	"""Algoritmo Diametro para encontrar o par de pontos mais distantes

	Ele consiste de:
	- determinar o fecho convexo dos pontos passados
	- determinar o conjunto de pares antipodas do fecho convexo
	- determinar o par antipoda cujos pontos estao a uma distancia maxima
	"""

	if len (l) < 2: return None
	if len (l) == 2:
		ret = Segment (l[0], l[1])
		ret.extra_info = 'distancia: %.2f'%math.sqrt (dist2 (l[0], l[1]))
		return ret
	
	ch = Graham (l)
	ch.hide ()
	ch.plot (config.COLOR_ALT4)

	control.sleep ()

	pairs = antipodes (ch)
	cores = (config.COLOR_ALT1,)

	#print `pairs`

	i=0
	for p,q in pairs:
		p.hilight (cores[i])
		q.hilight (cores[i])
		p.lineto (q, cores[i])
		i = (i+1) % len (cores)

	control.sleep ()

	farthest = dist2 (pairs[0][0], pairs[0][1])
	a = pairs[0][0]
	b = pairs[0][1]
	hia = a.hilight ()
	hib = b.hilight ()
	id = a.lineto (b)

	for i in range (1, len (pairs)):
		dist = dist2 (pairs[i][0], pairs[i][1])
		if dist > farthest:
			control.freeze_update ()
			a.unhilight (hia)
			b.unhilight (hib)
			control.plot_delete (id)

			farthest = dist
			a = pairs[i][0]
			b = pairs[i][1]

			hia = a.hilight ()
			hib = b.hilight ()
			id = a.lineto (b)
			control.thaw_update ()
	
	ret = Segment (a, b)
	ret.extra_info = 'distancia: %.2f'%math.sqrt (farthest)
	return ret
def Graham (l):
	"Algoritmo de Graham para achar o fecho convexo de uma lista l de pontos"

	if len (l) == 0: return None

	# So um ponto foi passado. Retorna um fecho c/ apenas um ponto
	if len (l) == 1:
		ret = Polygon (l)
		ret.plot ()
		ret.extra_info = 'vertices: 1'
		return ret

	p0 = l[0]

	# acha o ponto mais baixo
	for i in range (1, len(l)):
		if l[i].y < p0.y:
			p0 = l[i]
		elif l[i].y == p0.y:
			if l[i].x > p0.x:
				p0 = l[i]

	l.remove (p0)

	def cmp (x, y, z = p0):
		"""Funcao para ordenar os pontos ao redor de z

		Usada com a funcao sort, ordena os pontos de uma lista
		de acordo com o angulo que cada ponto forma com o ponto 
		z e a reta horizontal. Em caso de empate, o ponto mais
		distante aparece primeiro."""
		area = area2 (z, x, y)
		if area > 0:
			return -1
		elif area < 0:
			return 1
		else:
			dist_z_x = dist2 (z, x)
			dist_z_y = dist2 (z, y)
			if dist_z_y < dist_z_x:
				return -1
			return dist_z_y > dist_z_x

	# Ordena os pontos pelo seus angulos
	l.sort (cmp)

	# eliminando pontos colineares
	l2 = [ l[0] ]
	for i in range (1, len (l)):
		if collinear (p0, l[i-1], l[i]):
			continue
		l2.append (l[i])

	l = l2

	# So sobraram dois pontos -> retorna fecho c/ os dois
	if len (l) < 2:
		ret = Polygon ( [ p0, l[0] ] )
		ret.plot ()
		ret.extra_info = 'vertices: 2'
		return ret

	pilha = [ p0, l[0], l[1] ]

	p0.lineto (l[0])
	l[0].lineto (l[1])
	control.sleep ()

	for i in range (2, len(l)):
		l[i].hilight ()
		pilha[-1].lineto (l[i])
		control.sleep ()

		while not left (pilha[-2], pilha[-1], l[i]):
			pilha[-2].remove_lineto (pilha[-1])
			pilha[-1].remove_lineto (l[i])

			pilha.pop ()

			pilha[-1].lineto (l[i])
			control.sleep ()


		pilha.append (l[i])

		l[i].unhilight ()
		
	pilha[-1].lineto (pilha[0])
	

	for i in range (0, len(pilha)-1):
		pilha[i].remove_lineto (pilha[i+1])

	pilha[-1].remove_lineto (pilha[0])
	poligono = Polygon (pilha)
	poligono.plot ()
	control.thaw_update ()

	poligono.extra_info = 'vertices: %d'%len (poligono.to_list ())
	return poligono
Beispiel #60
0
def verticesVisiveis(p, poligs):
	pontos = []
	for i in range(len(poligs)):
		pontos.extend(poligs[i].to_list())
	compara = criaCompara(p)

	#Intersecta p.x -> inf+
	T = Tree();

	pontos.sort(key = cmp_to_key(compara), reverse = True)
	for i in range(len(poligs)):
		listaPs = poligs[i].to_list()
		n = len(listaPs)
		for j in range(n):
			a = listaPs[j]; b = listaPs[(j+1)%n];
			if(passaEixoX(a, b, p)):
				if(left_on(p,b,a)): T.insert(Segment(a,b));
				else: T.insert(Segment(b,a));

	W = []; 
	for i in range(len(pontos)):
		a = pontos[i]

		idBranco = p.lineto(a, 'white')
		a.hilight('yellow')
		control.sleep()
		a.hilight('red')
		a.unhilight()

		if(visivel(T, pontos, p, i)): 
			if(a is not p):
				W.append(a)
				p.remove_lineto(a, idBranco)
				p.lineto(a, 'blue')
			else: continue; 
		else: p.remove_lineto(a, idBranco)



		
		b = a.prev; c = a.next;
		
		if( a.x == b.x and a.y == b.y): continue #a não está em um
												#polígono		
		if(left_on(p,a,b)):
			T.delete(Segment(b,a))
	
		if(left_on(p,a,c)): 
			T.delete(Segment(c,a))

		else:
			T.insert(Segment(a,c))

		#else do primeiro if
		#Tentando evitar q na hora da inserção tenha segmentos terminando
		#na linha de varredura.
		if(right(p,a,b)): 
			T.insert(Segment(a,b))


	return W