16 de agosto de 2010

Traçando rotas com a versão 3 da API do Google Maps

Usar a versão 3 da API do Google Maps para traçar a rota entre dois endereços envolve basicamente os mesmos procedimentos descritos no post "Usando a versão 3 da API do Google Maps" aos quais se acrescenta o uso de um objeto específico da API para traçar a rota - o DirectionsService.

Mas, vamos por partes. Como já disse naquele post, a API é disponibilizada como um conjunto de classes e outros códigos JavaScript. Então, o local deste script precisa ser indicado no HTML:

<script type="text/javascript" src="http://maps.google.com/maps/api/js?v=3.1&sensor=false&language=pt-BR"></script>

Também precisaremos de instâncias dos dois objetos principais da API - o que representa o mapa em si e o Geocoder, responsável pela conversão entre endereços reais e suas respectivas coordenadas (latitude/longitude).
var map, geocoder;
function initialize() {
var lOptions = {zoom: 15,
mapTypeId: google.maps.MapTypeId.ROADMAP};
var lMapNode;
lMapNode = document.getElementById('map_canvas');
map = new google.maps.Map(lMapNode, lOptions);
geocoder = new google.maps.Geocoder();
}

function trataLocais (results, status) {
if (status == google.maps.GeocoderStatus.OK) {
map.setCenter(results[0].geometry.location);
var marker = new google.maps.Marker({map: map, position: results[0].geometry.location });
}
}

Apenas para lembrar, o nome 'map_canvas' identifica uma tag HTML do tipo DIV. Com isso, mostrar um endereço no mapa se restringe ao código javascript abaixo.
var lEndereco;
var lRequest;

lEndereco = 'ALAMEDA SANTOS, 1000, SÃO PAULO - SP, 01418-9028';
lRequest = { address: lEndereco, region: 'BR'};

geocoder.geocode( lRequest, trataLocais);

Até aqui, o processo foi o mesmo descrito no outro post. No entanto, traçar a rota não exige muito mais que isso. Para esse recurso funcionar, temos que instanciar o serviço de cálculo de rotas do Google Maps e o serviço que exibe uma rota calculada. Depois, basta solicitar ao primeiro que trace a rota entre dois endereços fornecidos:
var directionsService;
var directionsRenderer;

directionsService = new google.maps.DirectionsService();

directionsRenderer = new google.maps.DirectionsRenderer();
directionsRenderer.setMap(map);

var enderDe = 'ALAMEDA SANTOS, 1000, SÃO PAULO - SP, 01418-9028';
var enderAte = 'AVENIDA NAÇÕES UNIDAS, 17-17, BAURU - SP, 17013-035';

var request = {
origin:endDe,
destination:endPara,
travelMode: google.maps.DirectionsTravelMode.DRIVING
};

directionsService.route(request, function(response, status) {
if (status == google.maps.DirectionsStatus.OK) {
directionsRenderer.setDirections(response);
}
});)

Veja que é o serviço de exibição quem é conectado ao mapa. Como o serviço que traça a rota apenas realiza os cálculos, este não precisa conhecer o mapa que está instanciado. Veja também que foi necessário construir uma requisição com as informações sobre a rota que se deseja traçar. Esta requisição é um objeto do tipo DirectionsRequest, que oferece opções para refinar a rota. Além do endereço de origem para a rota e o seu destino, é exigido da requisição que se estipule o meio de transporte a ser utilizado para ir de um endereço a outro. Nesta versão da API, as possibilidades são ir de carro (como no exemplo), ir de bicicleta ou andando. Outros ajustes disponíveis na requisição permitem configurar a rota para evitar estradas pedagiadas e fornecer rotas alternativas.

Outro ponto a destacar é o segundo parâmetro da função route, responsável pelo cálculo da rota. Este parâmetro é uma função que devemos usar para receber os dados da rota calculada e um status desse cálculo. Caso o status seja OK, basta passar os dados calculados ao serviço de exibição, fechando o ciclo.

Esse procedimento resulta no seguinte mapa:


O HTML com este exemplo pode ser acessado neste link.

Um outro recurso útil a ser adicionado é o que descreve como seguir a rota, da mesma maneira que um aparelho de GPS narra as direções a tomar e distâncias a percorrer. Para isso, crie uma nova tag DIV no seu HTML - digamos que você a identifique como panel. Basta, então, configurar o serviço de exibição, indicando-lhe qual a tag onde descrever a rota. Apenas uma linha, como segue:
directionsRenderer.setPanel(document.getElementById("panel"));


55 comentários :

Adestrador Cristiano Bier disse...

Tenho um pequeno negócio de entrega de rações e serviço de pet-táxi. Para cálculo do pet-táxi necessito saber a quilometragem de minha casa até o cliente, do cliente até o destino, do destino até a casa do cliente e da casa dele até a minha. Há uma forma de ser feito e inserido no site? Gostaria de que o clinte colocasse seu cep ou endereço, o cep ou o endereço de detino e o sistema já tivesse meu cep gravado. Não haveria necessidade de aparecer mapas na tela. Apenas meu orçamento feito no excel. É complicado, né?

Luís Gustavo Fabbro disse...

Cristiano

Dê uma olhada no post Informações sobre rotas com a versão 3 da API do Google Maps. Ele trata do cálculo da distância entre endereços, enquanto te permite optar por mostrar o mapa ou dispensar a apresentação.

Como o código é javascript, você pode usá-lo no seu site.

[]s

BeStore - Blog Commerce disse...

Bom dia,

vi no seu site, que voce ensina como usar alguns recursos da api v3 do google.. então eu gostaria de saber como ficaria o uso desta APi se fosse extraido uma rota de um documento xml, ou de um banco de dados onde temos um historio de lat e long.

Hoje que uso a versão 2 da api, e eu gero um arquivo XML, vindo de um banco de dados OBDC que por sua vez gera um arquivo.xml, com as latitudes e longitudes.. e mostro em forma de marcador no google mapas.

**Estou construindo um sistema de rastreamento...

Então, gostaria de saber como fazer este procedimento usando a api v3. // Faco estes procedimentos para ASP.NET e C#

Pode me ajudar? Segue o codigo abaixo..

// PARTE DE CARREGAMENTO DO SERVICO DO GOOGLE MAPAS // CARREGAMENTO DO SISTEMA DE RASTREAMENTO //


var map;

google.load("maps", "10", { "other_params": "sensor=true" });

function initialize() {
if (GBrowserIsCompatible()) {
var map = new google.maps.Map2(document.getElementById("map"));
map.addControl(new GSmallMapControl());
map.addControl(new GMapTypeControl());
map.setCenter(new GLatLng(-23.5489433, -46.6388182), 10);
map.addMapType(G_PHYSICAL_MAP);
// map.setMapType(G_PHYSICAL_MAP);

GDownloadUrl("Scripts/Landmarks.xml", function (data) {
var xml = GXml.parse(data);
var markers = xml.documentElement.getElementsByTagName("marker");

for (var i = 0; i < markers.length; i++) {
var latlng = new GLatLng(parseFloat(markers[i].getAttribute("lat")),
parseFloat(markers[i].getAttribute("lng")));


descricao = markers[i].getAttribute("descricao");

var marker = createInfoMarker(latlng, descricao);
map.addOverlay(marker);
}
});
}
}
google.setOnLoadCallback(initialize);

function createInfoMarker(point, address) {
var marker = new GMarker(point);
GEvent.addListener(marker, "click", function () {
marker.openInfoWindowHtml(address);
});
return marker;
}


// FIM DA PARTE DE CARREGAMENTO DO SISTEMA MAPS.//

// arquivo XML. gerado do banco.












..

Obrigado,

Luís Gustavo Fabbro disse...

Rodrigo

Que parte do processo você não conseguiu montar ?

Os procedimentos iniciais para utilizar a API e traçar rotas estão no post acima. O exemplo mostra o uso informando-se os endereços reais mas a requisição de rota também admite o uso do par latitude/longitude – veja a documentação em https://developers.google.com/maps/documentation/javascript/reference?hl=pt-br#DirectionsRequest.

Se o problema é o download do XML, dê uma olha nesse exemplo : http://gmaps-samples-v3.googlecode.com/svn/trunk/xmlparsing/downloadurl.html. Ele usa a função downloadUrl, similar ao GDownloadUrl, disponível no javascript http://gmaps-samples-v3.googlecode.com/svn/trunk/xmlparsing/util.js.

Quanto aos marcadores, eles são incluídos automaticamente no mapa para cada ponto da rota. Você pode suprimí-los ou alterar a configuração padrão deles através das opções dos marcadores : https://developers.google.com/maps/documentation/javascript/reference?hl=pt-br#DirectionsRendererOptions. Tais opções podem ser passadas ao DirectionsRenderer através da função setOptions.

Att.

Elinardy disse...

Boa tarde,
Trabalho em uma escola, e utilizando o banco de dados com os endereços dos alunos, marcar no mapa da cidade onde os mesmo moram. Tendo uma ideia de qual bairro tem mais alunos e assim por diante. Mas que isso utiliza-se o google maps ou alguma ferramente gratuita.
Dei uma lida no que a respeito da API do google, tem como eu fazer esse tipo de configuração? E se é muito complicado, não sou bom em programação.

Luís Gustavo Fabbro disse...

Elinardy

É possível montar um mapa com a API do Google e marcar quantos endereços forem necessários. Dê uma olhada no post Usando a versão 3 da API do Google Maps que trata do básico sobre mapas com essa API, incluindo a marcação de endereços.

[]s

Anônimo disse...

Boa noite Luis Gustavo

É possivel fazer a requisição de rotas atraves de comandos em C?
O maximoq que conseguimos foi em javascript e html usando edits e passando por parametros.
Agradeço pela atenção

Luís Gustavo Fabbro disse...

Se o seu objetivo é exibir rotas em um programa C, pode usuar o COM do Internet Explorer e interagir com o HTML que exibe a rota. Ha um exemplo em Delphi/C++ Builder no link http://balaiotecnologico.blogspot.com.br/2010/02/interagindo-com-html-em-programas.html; como se trata de um COM, as propriedades e funções apresentadas valem pra qualquer linguagem que suporte o COM.

Mas, se o que você quer é recuperar em C as informações de uma rota pra poder manipulá-las diretamente em seu programa, terá que submeter requisições HTTP com a API do Google. Há algumas considerações sobre isso neste link mas terá que pesquisar a sintaxe da API do Google pra mapas e rotas.

[]s

Juninho Corinthiano disse...

E caso eu queia fazer com vários endereços?

Luís Gustavo Fabbro disse...

Juninho

O post Traçando rotas com a versão 3 da API do Google Maps - Parte II mostra como traçar rotas passando por uma lista de endereços conhecidos.

[]s

Anônimo disse...

Bom dia Luis, existe alguma forma de além dele retornar o mapa do google maps ele retonar a distancia e o tempo previsto ?

Luís Gustavo Fabbro disse...

Dê uma olhada no post Informações sobre rotas com a versão 3 da API do Google Maps. Ele mostra como obter essas informações até mesmo sem precisar desenhar o mapa, se necessário.

[]s

Anônimo disse...

olá sabe me informar pq se eu opto colocar coordenadas (latitude e longetude) no lugar do endereço ele nao funciona ou melhor funciona apenas se coloco no endereço de partida

ex.

var enderDe = new google.maps.LatLng(,);

//nesse aqui tenho que colocar asim se coloco apenas coordenadas como o anterior nao carrega o mapa
var enderAte = ', , - , ';

Luís Gustavo Fabbro disse...

Há um exemplo com esse tipo de construção usando latitude e longitude nest link. Reveja seu código pois o problema deve estar em outro ponto.

[]s

Anônimo disse...

Olá você saberia me informar, se teria como fazer uma pesquisa por endereços utilizando a api?
Por exemplo, eu escrevo av brasil, e a api me traria um o resultado de todas as "av brasil" que ele achou.

Anônimo disse...

Olá você sabe se tem alguma função nesta api que busca endereços?
Por exemplo eu informo "av brasil - sao paulo" e a api me retorna todos os resultados que tem "av - brasil".
Gostaria de montar uma ferramenta de autocomplete para evitar erros dos usuários na hora de digitar o endereço

Luís Gustavo Fabbro disse...

Luan

Quando você usa a função geocode, ela repassa para uma função sua uma lista com os endereços que ela localizou. No exemplo, esses resultados são passados para a minha função trataLocais mas, como eu sei que o endereço fornecido é único, eu acesso apenas a posição 0 da lista retornada (o results). Se a informação que você passar não for suficiente para determinar um endereço único, results conterá uma lista de sugestões.

Anônimo disse...

Boa Tarde,

como faco para pegar o CEP
eval(" var marker"+i+" = new google.maps.Marker({map: map, position: results[i].geometry.location, title: results[i].geometry.location.toString()});");
eval(" google.maps.event.addListener(marker"+i+", 'click', function() { infowindow"+i+".open(map); }); ");

eval(" alert( results[i].geometry.location.lat() ) ");
eval(" alert( results[i].geometry.location.lng() ) ");
eval(" alert( results[i].address_components.long_name ");

Luís Gustavo Fabbro disse...

A propriedade formatted_address em cada resultado traz as partes do endereço separadas por vírgula (rua, cidade, CEP, país). Você pode aplicar a função split do javascript a esse endereço e obter cada parte separadamente num array. Ex:

var i, parts;
parts = results[0].formatted_address.split (",");

for (i = 0; i < parts.length; i ++)
alert (parts[i]);

Anônimo disse...

Existe como eu pegar a km ?

Luís Gustavo Fabbro disse...

O post Informações sobre rotas com a versão 3 da API do Google Maps mostra como obter tanto a distância em cada etapa do trajeto como a distância total em kms.

[]s

Anônimo disse...

Luís Gustavo,
Eu gostaria de saber como eu faço para pegar informações sobre Linhas de Ônibus, Taxis e Trens
na documentação tem a Referência de: google.maps.TransitLine object ;

Porém não existe exemplo de como aplicar tal classe; se puder dar uma ajuda estarei grato,

Encarecidamente,

Luís Gustavo Fabbro disse...

Você pode obter informações sobre rotas com transporte público solicitando a rota com travelMode ajustado para TRANSIT, opção existente nas versões mais recentes da API do Google Maps. Ao invés de v=3.1, use o script com parâmetro v=3.9 para que a opção seja reconhecida.

Onde houver disponibilidade, serão retornadas as opções de rota com transporte público entre os endereços fornecidos. Detalhes do transporte público estarão na propriedade transit de cada "perna" do trajeto. Há um exemplo de como navegar pelas "pernas" no post Informações sobre rotas com a versão 3 da API do Google Maps.

[]s

Unknown disse...

Oi.

Como eu faço para pegar a Km entre dois endereços e jogar em uma variável do tipo Double?

Obrigado.

Luís Gustavo Fabbro disse...

O post Informações sobre rotas com a versão 3 da API do Google Maps mostra como obter tanto a distância em cada etapa do trajeto como a distância total em kms.

O exemplo lá usa javascript para somar as distâncias de cada fase do trajeto. Ou seja, você não precisa se preocupar se a variável é double ou não pois a linguagem cuidará disso automaticamente.

[]s

Anônimo disse...

Boa tarde!
Pessoal, alguém saberia me dizer por favor, se eu consigo carregar várias ruas pintadas em azul com essa API do Google?Eu precisaria carregar pintado na tela, todas as ruas de um determinado bairro em azul, como se fosse aquela linha que aparece quando calculamos a rota de um ponto a outro.
É que pretendo utilizar a API do Google Maps para resolver o problema do carteiro chinês para o meu TCC, mas se não tiver como fazer esses desenhos sobre o mapa, vou ter que abandonar essa idéia.

Muito Obrigado.

Luís Gustavo Fabbro disse...

Uma solução alternativa seria criar uma Polyline ou um Polygon sobre o mapa, criando uma linha fechada para delimitar o bairro. Você precisaria de uma série de pontos latitude/longitude para construir a linha.

[]s

Informatica disse...

Boa noite eu preciso traçar a rota de um ponto a outro mas eu preciso que seja digitado em campo de texto os endereco de origem e o endereço de destino e que ele mostre a rota que ele tera que fazer igual o como chegar do google maps, poderia me dar uma ajuda?

Luís Gustavo Fabbro disse...

A diferença básica do que você quer fazer em relação ao que está no post é que no post os endereços estão fixos no script. Basta, então, que vc crie os campos texto e um botão na página e, no evento de "clique" do botão, coloque o mesmo código do post, trocando os endereços fixos pelo valor de cada um dos campos.

[]s

Informatica disse...

Você poderia explicar melhor o que eu coloco nessa parte q vc disse ( no evento de "clique" do botão, coloque o mesmo código do post, qual parte do código seria?), e nessa parte aqui (trocando os endereços fixos pelo valor de cada um dos campos, oque precisaria fazer) desculpa pela pergunta mas só iniciante em programação e não entendo muito, se puder explicar um pouquinho melhor agradeço.

Informatica disse...

queria te mandar a parte que tenho do codigo mas o comentario nao aceita codigo html, teria alguma forma de te enviar o pedaço de codigo, meu email para vc entrar em contato se ouder para me dar uma ajuda e um pequeno trabalho da faculdade q tenho q fazer.
obrigado

Luís Gustavo Fabbro disse...

Seria algo nos moldes do exemplo do link http://www.w3schools.com/jsref/tryit.asp?filename=tryjsref_onclick. No lugar do Myfunction que há no link, vc incluiria o trecho do geocoder.geocode, mantendo as outras partes do código deste post.

Vc teria ainda que substituir o valor fixo atribuído ao enderDe e enderAte por algo como:

var enderDe = eval('ender1').value;

onde ender1 é o ID que vc colocou para a a caixa de texto para receber um endereço em seu HTML.

[]s

Luís Gustavo Fabbro disse...

Vc pode enviar email direto para o endereço do blog que consta no topo à direita, èm baixo da área do "Quem sou Eu?".

[]s

Anônimo disse...

OLá Luís Gustavo, poderia me tirar uma dúvida por favor, no mapa se eu quiser trocar essa imagem de balão com letra, que esta em cada ponto, por uma outra imagem qualquer tem como?

Luís Gustavo Fabbro disse...

Você pode criar marcações no mapa usando a classe Marker e usar um dos ícones disponíveis na API ou até mesmo informar a URL completa de uma imagem personalizada. Veja um exemplo no post Trabalhando com marcações em mapas com a versão 3 da API do Google Maps

[]s

Anônimo disse...

olá luis gustavo, sabe como obter coordenadas de um gps para o google maps? estou a desenvolver um programa de rastreamento que basicamente tem que ir buscar as coordenadas a um gps e actualizar automaticamente no meu mapa (ficheiro php) de x em x tempo (por exempo 5 em 5 minutos)

Luís Gustavo Fabbro disse...

André

O exemplo no post mostra o uso da API informando-se endereços reais mas a requisição também com um par latitude/longitude – veja a
documentação do GeocoderRequest. Há um exemplo básico no post neste endereço.

Em relação ao tempo, vc pode usar o setTimeout do JavaScript e refazer nele o mapa de acordo com a posição reportada pelo GPS.

[]s

Diego Ferreira disse...

olá luiz estou com um problema
tenho um codigo que faz rotas entre cidades mas quando passo endereços nunca funciona.
usei o seu exemplo e acontece a mesma coisa a menos que eu tenha as coordenadas dos pontos de inicio e fim da rota tanto seu exemplo quanto meu programa não funcionam.
fiz um teste na pagina do google maps e deu certo então imagino que seja algo com nossos codigos
passo sempre "rua, numero, bairro, cidade, estado"
talvez meu erro esteja aí
se puder ajudar...
abraços

Luís Gustavo Fabbro disse...

Zangets

Segundo a documentação da API, os endereços informados devem estar de acordo com o sistema de endereçamento postal do país ao qual pertence o local procurado. Não tenho certeza se no Brasil o bairro é parte obrigatória do sistema postal...

Entretanto, como pelo site do Maps vc diz que funcionou, pode ser que ele use um mecanismo diferente, como por exemplo a API server side ou o web service de geocoding (https://developers.google.com/maps/documentation/geocoding/index).

Veja o FAQ em https://developers.google.com/maps/faq para mais detalhes.

[]s

Douglas disse...

Luís Gustavo, tem como colocar um input e fazer a variável "enderDe" puxar o valor desse input.
Estou tentando fazer isso mas to com dificuldade.

Segue o link do que eu estou tentando fazer:
http://oarmazemdeideias.com.br/aero/como-chegar.html

Se tiver como, você me explica?

Luís Gustavo Fabbro disse...

Douglas

Qual é sua dificuldade? Em princípio, a solução básica tem uma implementação bastante simples. Basta criar 2 inputs em seu HTML - um para a caixa de texto e outro para o botão. No evento onclick do botão, chame uma função javascript que recupere o valor da caixa de texto:

/* No HTML */
<input type="text" id="edEnderDe" />
<input id="tracar" type="button" value="Traçar" onclick="tracaRota();">

/* No javascript: */
function tracaRota()
{
var enderDe = eval('edEnderDe').value;
/* ... */
}


[]s

Anônimo disse...

Olá Luiz, é possível inserir uma nova rota no mapa mantendo a anterior? Ex. eu adiciono a rota do ponto A ao ponto B e depois do B ao C mantendo todas as rotas?. Obrigado.

Luís Gustavo Fabbro disse...

Leandro

Você pode criar uma nova camada para exibir outra rota. Basta instanciar um novo DirectionsRenderer e usar o setDirections dele com o resultado do cálculo de rota do directionsService.

É possível até mesmo alterar as características de exibição dessa nova rota para diferenciá-la visualmente da rota traçada antes. Para isso, ajuste o DirectionsRendererOptions dela conforme a necessidade.

[]s

Anônimo disse...

Como eu pego o resultado do cálculo de rota do directionsService? Você tem algum exemplo de código?

Obrigado.

Luís Gustavo Fabbro disse...

Leandro

Como mostra o post, a rota é calculada pela função route do directionsService. O resultado desse cálculo é disponibilizado para a função de calback que vc cria e passa junto como parâmetro para a própria route. Veja o exemplo nesse post mesmo.

[]s

Unknown disse...

Luís

Eu estou fazendo uma monografia nela vou disponibiliza dados SIG e também pretendo fazer um google maps, no google maps eu quero colocar rotas e street view, você tem tutorial para me ajuda por favor.

Luís Gustavo Fabbro disse...

Antoniel

Há alguns outros posts no blog mostrando vários recursos do Google maps, desde o básico (configurações necessárias no html e como mostrar um local no mapa) até recursos de rotas (incluindo como obter informações de uma rota, marcações especiais e rotas com paradas intermediárias) e como personalizar a apresentação do mapa.

Você pode localizá-los no blog procurando por "Google maps" na caixa de pesquisa que está na parte superior direita.

Você também pode encontrar um tutorial formal na página do desenvolvedor do Google : https://developers.google.com/maps/documentation/javascript/tutorial?csw=1.

[]s

Shopcdmix News disse...

Prezado Luís Gustavo Fabbro

Qual sua dica para que eu apresente os dados de km e minutos entre dois pontos em um script que estou fazendo em ASP ? o melhor seria guardar os dados em uma session, é possível ?

Muito obrigado pela atenção.

Luís Gustavo Fabbro disse...

Você pode extrair as informações de uma rota sem precisar exibi-la num mapa em sua página. Há um post no blog tratando dessa técnica : Informações sobre rotas com a versão 3 da API do Google Maps.

[]s

Anônimo disse...

Como eu faço para traçar mais de uma rota

Luís Gustavo Fabbro disse...

Wilton

Você pode criar uma nova camada para exibir a nova rota enquanto mantem as preexistentes ativas. Basta instanciar um novo DirectionsRenderer e usar o setDirections dele com o resultado do cálculo de rota do directionsService (como no exemplo do post).

É possível até mesmo alterar as características de exibição dessa nova rota para diferenciá-la visualmente da(s) rota(s) traçada antes. Para isso, configure um DirectionsRendererOptions de acordo com a sua necessidade.

[]s

R.w :: Criação de Sites disse...

Olá Luís, esse assunto é muito interessante nos dias de hoje.
Apps ajudam a todos por todos os lados.

Gostaria de saber, como fazer uma pesquisa pra determinada cidade e buscar os ônibus da mesma.

Obrigado por compartilhar conhecimento.

R.w :: Criação de Sites disse...

Desculpe.

Esqueci de marcar o notifique. Nesse mensagem é apenas pra isso.

Obrigado novamente.

Luís Gustavo Fabbro disse...

Dependendo da cidade, é possível obter informações sobre opções de transporte público disponível para uma a rota.
Basta solicitar a rota com o valor de travelMode igual a TRANSIT.

As alternativas de trajeto usando transporte público serão retornadas e você pode percorrer os passos de cada um (como exemplificado no post Informações sobre rotas com a versão 3 da API do Google Maps), extraindo os dados contidos na estrutura TransitDetails de cada leg das rotas.

[]s

R.w :: Criação de Sites disse...

Legal!

Bom, é isso então.
Obrigado por compartilhar.

Abs.

Postar um comentário

OBS: Os comentários enviados a este Blog são submetidos a moderação. Por isso, eles serão publicados somente após aprovação.

Observação: somente um membro deste blog pode postar um comentário.