import geopandas as gpd import json import sys import folium import requests import re import shutil def internet_disponivel(): """Verifica se há conexão com a internet.""" url = 'http://www.google.com/' timeout = 5 try: _ = requests.get(url, timeout=timeout) return True except requests.ConnectionError: return False # Argumentos e configurações iniciais pathFiles = sys.argv[1] fileName = sys.argv[2] outputName = sys.argv[3] outputMapName = sys.argv[4] topico_gps = sys.argv[5] topico_ruas = sys.argv[6] topico_trajeto_dinamico = sys.argv[7] mapa_dados_json = sys.argv[8] pastaSaida = 'Python/Output/' if mapa_dados_json == "0": # Carregar o arquivo shapefile contendo a geometria input_shapefile = pathFiles + fileName + '.shp' data_geometry = gpd.read_file(input_shapefile) # Converter o GeoDataFrame para GeoJSON e adicionar ao mapa geojson_data = data_geometry.to_json() # Calcular os limites (bounds) da geometria minx, miny, maxx, maxy = data_geometry.total_bounds center = [(miny + maxy) / 2, (minx + maxx) / 2] # Salvar GEOJson data_geometry.to_file(pastaSaida + outputName, driver='GeoJSON') else: # Lendo os dados JSON with open(pathFiles + fileName + '.json', 'r', encoding='utf-8-sig') as f: geojson_data = json.load(f) # Obter os limites (bounds) dos dados GeoJSON bounds = folium.GeoJson(geojson_data).get_bounds() center = [(bounds[0][0] + bounds[1][0]) / 2, (bounds[0][1] + bounds[1][1]) / 2] # Adicionando um ID sequencial a cada Feature for idx, feature in enumerate(geojson_data["features"]): # Adicionar uma propriedade 'id' para cada Feature começando do índice zero feature['id'] = idx # Copiando o arquivo JSON para a pasta de saída shutil.copy(pathFiles + fileName + '.json', pastaSaida + outputName) # Verificar se há conexão com a internet if internet_disponivel(): m = folium.Map(location=center, zoom_start=12) else: m = folium.Map(location=center, zoom_start=12, tiles=None) folium.GeoJson(geojson_data).add_to(m) # Salvar o mapa interativo em um arquivo HTML m.save(pastaSaida + outputMapName) # Caminho completo para o arquivo HTML gerado caminho_completo_html = pastaSaida + outputMapName # Abrir o arquivo HTML para leitura e escrita with open(caminho_completo_html, 'r+') as arquivo_html: # Ler o conteúdo do arquivo conteudo_html = arquivo_html.read() # Usar expressão regular para encontrar o ID do mapa padrao_id_mapa = re.compile(r'id="map_(.*?)"') resultado_busca = padrao_id_mapa.search(conteudo_html) # Verificar se encontrou um ID de mapa if resultado_busca: id_mapa = 'map_' + resultado_busca.group(1) else: raise ValueError("Não foi possível encontrar o ID do mapa no arquivo HTML.") # Usar expressão regular para encontrar o ID da Trajetoria padrao_id_trajetoria = re.compile(r'var geo_json_(\w+)\s*=') resultado_busca_trajetoria = padrao_id_trajetoria.search(conteudo_html) # Verificar se encontrou um ID de trajetória if resultado_busca_trajetoria: id_trajetoria = 'geo_json_' + resultado_busca_trajetoria.group(1) else: # Adicionar mensagem de depuração para verificar o conteúdo do arquivo HTML raise ValueError("Não foi possível encontrar o ID da trajetória no arquivo HTML.") # Script para representar a trajetoria que o robô deve fazer até iniciar o trabalho script_desenha_trajetoria_dinamica = f""" """ # Script para desenhar o trajo percorrido no mapa script_desenha_trajeotria = f""" """ # Script JavaScript para adicionar ao HTML, com o ID do mapa substituído script_atualizacao_marcador = f""" """ # Primeiro, vamos definir o novo trecho de JavaScript que você quer adicionar funcao_define_ruas_selecionadas = f""" var trajetosSelecionados = {{}}; var RuasSelecionadas = []; function enviarSelecaoParaServidor() {{ client.publish("{topico_ruas}", JSON.stringify(RuasSelecionadas), function (err) {{ /*if (!err) {{ console.log("Mensagem publicada com sucesso"); }} else {{ console.error("Falha ao publicar mensagem", err); }}*/ }}); }} """ # Código para inserir dentro do layer.on({}) codigo_layer_on = """ click: function(e) { // Verificar se o trajeto já está selecionado if (trajetosSelecionados[feature.id]) { // Se já está selecionado, reverta para a cor original e remova da seleção e.target.setStyle({ color: '#3388ff' // Cor original }); delete trajetosSelecionados[feature.id]; RuasSelecionadas.splice(RuasSelecionadas.indexOf(feature.id), 1); } else { // Se não está selecionado, mude a cor para indicar seleção e adicione ao objeto de seleção e.target.setStyle({ color: 'blue' // Cor de seleção }); trajetosSelecionados[feature.id] = true; RuasSelecionadas.push(feature.id); } enviarSelecaoParaServidor(); }/*, mouseover: function(e) { // Mostrar tooltip com o ID da geometria quando o mouse passar sobre a linha var tooltip = L.tooltip({ direction: 'auto', // Leaflet determina a melhor posição sticky: true // Faz com que o tooltip siga o cursor do mouse }) .setContent('Rua ' + feature.id); // Define o conteúdo do tooltip // Abre o tooltip na posição atual do mouse var latLng = e.latlng; tooltip.setLatLng(latLng); layer.bindTooltip(tooltip).openTooltip(latLng); }*/ """ # Importar arquivos localmente conteudo_html = conteudo_html.replace('https://cdn.jsdelivr.net/npm/leaflet@1.9.3/dist/', 'folium/') conteudo_html = conteudo_html.replace('https://code.jquery.com/', 'folium/') conteudo_html = conteudo_html.replace('https://cdn.jsdelivr.net/npm/bootstrap@5.2.2/dist/js/', 'folium/') conteudo_html = conteudo_html.replace('https://cdnjs.cloudflare.com/ajax/libs/Leaflet.awesome-markers/2.0.2/', 'folium/') conteudo_html = conteudo_html.replace('https://cdn.jsdelivr.net/npm/leaflet@1.9.3/dist/', 'folium/') conteudo_html = conteudo_html.replace('https://cdn.jsdelivr.net/npm/bootstrap@5.2.2/dist/css/', 'folium/') conteudo_html = conteudo_html.replace('https://netdna.bootstrapcdn.com/bootstrap/3.0.0/css/', 'folium/') conteudo_html = conteudo_html.replace('https://cdn.jsdelivr.net/npm/@fortawesome/fontawesome-free@6.2.0/css/', 'folium/') conteudo_html = conteudo_html.replace('https://cdnjs.cloudflare.com/ajax/libs/Leaflet.awesome-markers/2.0.2/', 'folium/') conteudo_html = conteudo_html.replace('https://cdn.jsdelivr.net/gh/python-visualization/folium/folium/templates/', 'folium/') # Inserir o script no conteúdo HTML conteudo_atualizado = conteudo_html.replace('', script_desenha_trajeotria + script_desenha_trajetoria_dinamica + script_atualizacao_marcador + '') # Encontrar a posição onde inserir o novo trecho de JavaScript indice_inicio_funcao = conteudo_atualizado.find("function geo_json_") # Inserir o novo trecho de JavaScript antes da função conteudo_atualizado = conteudo_atualizado[:indice_inicio_funcao] + funcao_define_ruas_selecionadas + conteudo_atualizado[indice_inicio_funcao:] # Agora, para adicionar o código dentro do layer.on({}) # Você precisa encontrar o local exato. Isso pode ser um pouco mais complicado, pois pode haver várias ocorrências. # Uma abordagem seria encontrar a primeira ocorrência após o seu trecho inserido anteriormente. indice_layer_on = conteudo_atualizado.find("layer.on({", indice_inicio_funcao) # Verificar se encontrou o layer.on({}) if indice_layer_on != -1: # Encontrar a posição do fechamento do layer.on({}) indice_fechamento = conteudo_atualizado.find("});", indice_layer_on) # +1 para incluir a abertura da chave # Inserir o código dentro do layer.on({}) conteudo_atualizado = conteudo_atualizado[:indice_fechamento] + codigo_layer_on + conteudo_atualizado[indice_fechamento:] # Agora, reabrir o arquivo para escrita e sobrescrever o conteúdo com a versão atualizada with open(caminho_completo_html, 'w') as arquivo_html: arquivo_html.write(conteudo_atualizado)