﻿/*
* Busca de Plazza Brasil, desenvolvida por SnapSystems
* http://www.plazzabrasil.com.br/
* http://www.snapsystems.com.br/
*
* Copyright (c) 2009 Plazza Brasil
*
* Data: 2009-08-04
* Revisao: 1
*/

// contexto encapsulado autoexecutavel
(function() {
    // constante do caminho do webservice da busca
var MODULE_PATH = '/desktopmodules/buscaimoveis/WebService.asmx/';
    var MAP_ICON = "/desktopmodules/buscaimoveis/img/iconeMapa.png",
    MAP_ICON_WIDTH = 27,
    MAP_ICON_HEIGHT = 50;

    // contante do caminho da imagem do produto sem foto
    var URL_SEM_FOTO = '/desktopmodules/buscaimoveis/img/PlazaImagemnaodisponivel.jpg';

    // configuracao da busca
    var CONFIG = {

        // id dos containers dom
        CONTAINERS: {

            // containers do filtro
            FILTRO: {
                CarregarTiposProduto: '#selecaoCondicao',
                CarregarTiposNegocio: '#selecaoInteresse',
                CarregarTiposUso: '#selecaoFinalidade',
                CarregarTiposImovel: '#selecaoTipoImovel',
                CarregarCidadesComImoveis: '#selecaoCidades',
                CarregarZonas: '#selecaoZonas',
                CarregarZonasValor: '#selecaoBairros',
                CarregarAmbientes: '#selecaoAmbientes',
                CarregarCaracteristicas: '#selecaoCaracteristicas'
            },

            // containers da busca
            CONTEUDO: {
                PesquisarImoveis: '#' + $('#gridId')
            }
        },

        // metodos do webservice
        WEBSERVICES: {

            // metodos do filtro
            FILTRO: {
                CarregarTiposProduto: MODULE_PATH + 'CarregarTiposProduto',
                CarregarTiposNegocio: MODULE_PATH + 'CarregarTiposNegocio',
                CarregarTiposUso: MODULE_PATH + 'CarregarTiposUso',
                CarregarTiposImovel: MODULE_PATH + 'CarregarTiposImovel',
                CarregarCidadesComImoveis: MODULE_PATH + 'CarregarCidadesComImoveis',
                CarregarZonas: MODULE_PATH + 'CarregarZonas',
                CarregarZonasValor: MODULE_PATH + 'CarregarZonasValor',
                CarregarAmbientes: MODULE_PATH + 'CarregarAmbientes',
                CarregarCaracteristicas: MODULE_PATH + 'CarregarCaracteristicas',
                CarregarFiltroUsuario: MODULE_PATH + 'CarregarFiltroUsuario'
            },

            // metodos da busca
            CONTEUDO: {
                PesquisarImoveis: MODULE_PATH + 'PesquisarImoveis'
            }
        }
    };

    // cache das requisicoes
    var cache = [];

    // filtro da busca, instanciado no window
    var selecao = window.selecao = new Object();

    // classe Filtro
    // metodos e eventos de carregamento e manipulacao do DOM no filtro da busca
    var Filtro = window.Filtro = {

        // bind dos botoes/links do filtro
        selecao: function() {
            // obj jQuery com todos os elementos da classe 'selecionavel'
            var selecionaveis = $('.selecionavel'),

            // obj jQuery com todos os inputs da classe 'selecionavelInput'
		inputs = $('input.selecionavelInput'),

		bairro = $('select#selecaoBairros'),

            // referencia
                _this = this,

            // referencia jQuery
                $this,

            // array auxiliar
                arrAux = [];

            // evento change dos bairros
            bairro.change(function() {
                Filtro.serializar('ZonasValor', $(this).val());
            });

            // bind do evento click dos inputs
            inputs.live('click', function() {
                // o evento click do label sera disparado, marcando a selecao
                $(this).next().click();
            });

            // bind do evento click dos 'selecionaveis'
            selecionaveis.live('click', function(e) {
                // referencia do jquery
                $this = $(this);

                // reset do array auxiliar
                arrAux = [];

                // ativa o item clicado
                Filtro.ativarItem($(this));

                // carrega ZonasValor no click da cidade se o id do parent clicado for igual ao container
                if ($this.parent().parent().attr('id') == CONFIG.CONTAINERS.FILTRO.CarregarCidadesComImoveis.split('#')[1]) {
                    // esconde container das ZonasValor
                    _this.exibirContainer($(CONFIG.CONTAINERS.FILTRO.CarregarZonasValor));

                    // carrega filtro do metodo CarregarZonasValorPorCidade, codCidade como parametro
                    if ($this.hasClass('ativo'))
                        Filtro.carregarFiltro('CarregarZonasValor', { filtroBusca: { Cidade: $(CONFIG.CONTAINERS.FILTRO.CarregarCidadesComImoveis).find('a.ativo').attr('id').split('_')[1]} });
                }

                // carrega tipos de imovel se o id do parent clicado for igual ao container
                if ($this.parent().parent().attr('id') == CONFIG.CONTAINERS.FILTRO.CarregarTiposUso.split('#')[1]) {
                    // serializa tiposUso para enviar como parametro
                    $this.parent().parent().find('a.ativo').each(function(i) {
                        arrAux.push($(this).attr('id').split('_')[1]);
                    });

                    // carrega filtro do metodo CarregarTiposImovel passando codTipoUso como parametro
                    if ($this.hasClass('ativo'))
                        Filtro.carregarFiltro('CarregarTiposImovel', { filtroBusca: { TipoUso: arrAux.length == 0 ? 0 : arrAux} });
                }

                // serializa filtro passando nome do metodo e valor
                Filtro.serializar($this.attr('id').split('_')[0].replace('Carregar', '', 'gi'), $this.attr('id').split('_')[1]);

                // para evento default do click
                return false;
            });
        },

        // metodo de ativacao dos itens do filtro
        // recebe elemento jQuery
        ativarItem: function($this) {
            // se elemento anterior ao enviado tiver o atributo 'type' igual a 'radio'
            if ($this.prev().attr('type') == 'radio') {
                if ($this.hasClass('ativo')) {
                    // seta valor do input para vazio
                    //  $this.parent().parent().find('input:checked').attr('checked', '');
                    // remove a classe 'ativo'
                    // $this.parent().parent().find('a').removeClass('ativo');
                } else {
                    // seta valor do input para vazio
                    $this.parent().parent().find('input:checked').attr('checked', '');

                    // remove a classe 'ativo'
                    $this.parent().parent().find('a').removeClass('ativo');

                    // se o link nao tiver a classe 'ativo'
                    if (!$this.hasClass('ativo'))
                    // checa o input
                        $this.addClass('ativo').prev().attr('checked', 'checked');
                    else
                    // desmarca o input
                        $this.removeClass('ativo').prev().attr('checked', '');
                }
            } else {
                // se o link nao tiver a classe 'ativo'
                if (!$this.hasClass('ativo'))
                // checa o input
                    $this.addClass('ativo').prev().attr('checked', 'checked');
                else
                // desmarca o input
                    $this.removeClass('ativo').prev().attr('checked', '');
            }

            // retorna o elemento jQuery
            return $this;
        },

        // metodo para exibir container
        // recebe container
        exibirContainer: function(container) {
            container.removeClass('hide').prev().removeClass('hide');
        },

        // metodo para esconder container
        // recebe container
        esconderContainer: function(container) {
            container.addClass('hide').prev().addClass('hide');
        },

        // evento do slider
        slider: function() {
            // serializa o filtro passando o nome do metodo e o valor do slider como parametro
            Filtro.serializar(arguments[0]._clientStateFieldID.split('_')[3].replace('slider', '', 'gi'), typeof arguments[1]._newValue != 'undefined' ? arguments[1]._newValue : null);
        },

        // metodo de serializacao do filtro
        // recebe nome do parametro e valor a serializar
        serializar: function(parametro, valor) {
            // seta valores na selecao global
            // para cada parametro
            switch (parametro) {
                // metodo                                   
                case 'CidadesComImoveis':
                    // parametro recebe valor
                    selecao.Cidade = valor;
                    selecao.ZonaValor = '';
                    break;

                case 'TiposProduto':
                    if (typeof selecao.TipoProduto == 'undefined')
                        selecao.TipoProduto = new Array(valor);
                    else
                        if (inArray(valor, selecao.TipoProduto)) {
                        selecao.TipoProduto = eval('[' + selecao.TipoProduto + ']');
                        removerArray(valor, selecao.TipoProduto);
                    }
                    else {
                        selecao.TipoProduto = eval('[' + selecao.TipoProduto + ']');
                        selecao.TipoProduto.push(valor);
                    }

                    break;

                case 'TiposNegocio':
                    selecao.TipoNegocio = valor;

                    break;

                case 'TiposUso':
                    selecao.TipoUso = valor;

                    break;

                case 'TiposImovel':
                    if (typeof selecao.TipoImovel == 'undefined')
                        selecao.TipoImovel = new Array(valor);
                    else
                        if (inArray(valor, selecao.TipoImovel)) {
                        selecao.TipoImovel = eval('[' + selecao.TipoImovel + ']');
                        removerArray(valor, selecao.TipoImovel);
                    }
                    else {
                        selecao.TipoImovel = eval('[' + selecao.TipoImovel + ']');
                        selecao.TipoImovel.push(valor);
                    }
                    break;

                case 'ValorMaximo':
                    selecao.PrecoVenda = (valor * 1000);
                    break;

                case 'ValorMaximoAluguel':
                    selecao.PrecoLocacaoMaximo = valor;
                    break;

                case 'AreaMinima':
                    selecao.AreaPrivativa = valor;
                    break;

                case 'Dormitorios':
                    selecao.Dormitorios = valor;
                    break;

                case 'Suites':
                    selecao.Suites = valor;
                    break;

                case 'Vagas':
                    selecao.Vagas = valor;
                    break;

                case 'Zona':
                    selecao.Zona = valor;
                    break;

                case 'ZonasValor':
                    if (typeof selecao.ZonaValor == 'undefined')
                        selecao.ZonaValor = valor;
                    else
                        selecao.ZonaValor = valor;
                       
                    
                    break;

                default:
                    //do something
                    break;
            }

            // carrega busca passando a selecao global como parametro
            Busca.Conteudo.load({ filtroBusca: Filtro.limparSelecao() });
        },

        // metodo para excluir itens que sejam null ou '' da selecao
        limparSelecao: function() {
            for (var item in selecao)
                if (selecao[item] == null || selecao[item] == '')
                delete selecao[item];

            return selecao;
        },

        // metodo de carregamento dos filtros
        // recebe o metodo (webservice) e dados
        carregarFiltro: function(metodo, data) {
            var _this = this,
                buffer = [],
                arrAux = [],
                preEval;
            carregar = true;
            // se data for vazio instancia    
            data = data ? data : {};

            // se o metodo for CarregarTiposImovel, serializa itens para exibir menu TipoUso
            if (metodo == 'CarregarTiposImovel') {
                $(CONFIG.CONTAINERS.FILTRO['CarregarTiposUso']).find('a').each(function(i) {
                    buffer.push(parseInt($(this).attr('id').split('_')[1]));
                    if ($(this).hasClass('ativo'))
                        arrAux.push($(this).attr('id').split('_')[1]);
                });

                data = { filtroBusca: { TipoUso: arrAux.length == 0 ? null : arrAux[0]} };

                if (data.filtroBusca.TipoUso == undefined) {
                    carregar = false;
                    filtroStack++;
                }

            }

            data.codPortal = $('#codPortal').val();
            if (carregar) {
                // metodo ajax do jQuery
                $.ajax({
                    // url do webservice
                    url: CONFIG.WEBSERVICES.FILTRO[metodo],

                    // metodo de envio
                    type: 'post',

                    // JSON enviado como parametro
                    data: JSON.stringify(data),

                    // tipo de envio
                    dataType: 'json',

                    // tipo de dados recebido
                    contentType: 'application/json',

                    // callback de sucesso
                    success: function(jsonData) {
                        // faz parse dos imoveis
                        jsonData = JSON.parse(jsonData.d);

                        // escreve o filtro
                        _this.escreverFiltro(metodo, jsonData, jsonData.length == 0);

                        // se o metodo for TiposUso, carrega o metodo TiposImovel
                        if (metodo == 'CarregarTiposUso')
                            Filtro.carregarFiltro('CarregarTiposImovel', { filtroBusca: {} });

                        if (metodo == 'CarregarTiposImovel')
                            Filtro.ativarItem($('div#filtroBusca a[tipoimovel=' + window.TipoImovel + ']'));

                        // adiciona no stack
                        filtroStack++;
                        Cache.set(metodo, jsonData)
                    }
                });
            }
        },

        /* Escrever filtro */
        escreverFiltro: function(metodo, data, isEmpty) {
            // se for vazio, retorna
            if (typeof isEmpty == 'undefined') isEmpty = false;

            // container
            var containerHTML = $(CONFIG.CONTAINERS.FILTRO[metodo]),

            // template com checkbox
            templateCheckbox = '<li><input type="checkbox" class="selecionavelInput" /><a href="#" class="selecionavel" id="#id#" #atributo#="#valor#" title="#label#">#label#</a></li>',

            // template com radio
		    templateRadio = '<li><input type="radio" class="selecionavelInput" name="#metodo#" /><a href="#" class="selecionavel" #atributo#="#valor#" id="#id#" title="#label#">#label#</a></li>',

            // template com option
		    templateOption = '<option #atributo#="#valor#" id="#id#" title="#label#" value="#valor#" >#label#</option>',

            // temp de template
		tempTemplate;

            // limpa o container    
            containerHTML.html('');

            // se o metodo for
            if (metodo == 'CarregarTiposUso') {
                for (var k = 0; k < data.length; k++) {
                    tempTemplate = templateRadio;

                    tempTemplate = tempTemplate.replace(new RegExp('#label#', 'gi'), data[k].Nome);
                    tempTemplate = tempTemplate.replace(new RegExp('#id#', 'gi'), metodo + '_' + data[k].CodTipoUso);
                    tempTemplate = tempTemplate.replace(new RegExp('#metodo#', 'gi'), metodo);
                    tempTemplate = tempTemplate.replace(new RegExp('#atributo#', 'gi'), 'TipoUso');
                    tempTemplate = tempTemplate.replace(new RegExp('#valor#', 'gi'), data[k].CodTipoUso);

                    containerHTML.append(tempTemplate);
                }
            } else if (metodo == 'CarregarTiposImovel') {
                for (var k = 0; k < data.length; k++) {
                    tempTemplate = templateCheckbox;

                    tempTemplate = tempTemplate.replace(new RegExp('#label#', 'gi'), data[k].Nome);
                    tempTemplate = tempTemplate.replace(new RegExp('#id#', 'gi'), metodo + '_' + data[k].CodTipoImovel);
                    tempTemplate = tempTemplate.replace(new RegExp('#atributo#', 'gi'), 'TipoImovel');
                    tempTemplate = tempTemplate.replace(new RegExp('#valor#', 'gi'), data[k].CodTipoImovel);

                    containerHTML.append(tempTemplate);
                }
            } else if (metodo == 'CarregarCidadesComImoveis') {
                for (var k = 0; k < data.length; k++) {
                    tempTemplate = templateRadio;

                    tempTemplate = tempTemplate.replace(new RegExp('#label#', 'gi'), data[k].Nome);
                    tempTemplate = tempTemplate.replace(new RegExp('#id#', 'gi'), metodo + '_' + data[k].CodCidade);
                    tempTemplate = tempTemplate.replace(new RegExp('#metodo#', 'gi'), metodo);
                    tempTemplate = tempTemplate.replace(new RegExp('#atributo#', 'gi'), 'Cidade');
                    tempTemplate = tempTemplate.replace(new RegExp('#valor#', 'gi'), data[k].CodCidade);

                    containerHTML.append(tempTemplate);
                }
            } else if ((metodo == "CarregarZonasValor" || metodo == "CarregarZonasValorPorZona") && !isEmpty) {

                for (var k = 0; k < data.length; k++) {
                    if (k == 0) {
                        containerHTML.append('<option ZonaValor="" id="' + metodo + '" title="Selecione um bairro" value="">Selecione um bairro</option>')
                    }
                    tempTemplate = templateOption;
                    tempTemplate = tempTemplate.replace(new RegExp("#label#", "gi"), data[k].Nome);
                    tempTemplate = tempTemplate.replace(new RegExp("#id#", "gi"), metodo + "_" + data[k].CodZonaValor);
                    tempTemplate = tempTemplate.replace(new RegExp("#atributo#", "gi"), "ZonaValor");
                    tempTemplate = tempTemplate.replace(new RegExp("#valor#", "gi"), data[k].CodZonaValor);

                    containerHTML.append(tempTemplate)
                }
            }
            /*else if ((metodo == 'CarregarZonasValorPorCidade' || metodo == 'CarregarZonasValorPorZona') && isEmpty) {
            this.esconderContainer(containerHTML);
            }
            else if (metodo == 'CarregarZonasValor') {
            for (var k = 0; k < data.length; k++) {
            tempTemplate = templateOption;

                    tempTemplate = tempTemplate.replace(new RegExp('#label#', 'gi'), data[k].Nome);
            tempTemplate = tempTemplate.replace(new RegExp('#id#', 'gi'), metodo + '_' + data[k].CodZonaValor);
            tempTemplate = tempTemplate.replace(new RegExp('#atributo#', 'gi'), 'ZonaValor');
            tempTemplate = tempTemplate.replace(new RegExp('#valor#', 'gi'), data[k].CodZonaValor);

                    containerHTML.append(tempTemplate);
            }
            }*/
            else if (metodo == 'CarregarTiposProduto') {
                for (var item in data) {
                    tempTemplate = templateCheckbox;

                    tempTemplate = tempTemplate.replace(new RegExp('#label#', 'gi'), data[item].replace(new RegExp('Empreendimento', 'gi'), 'Lançamento'));
                    tempTemplate = tempTemplate.replace(new RegExp('#id#', 'gi'), metodo + '_' + item);
                    tempTemplate = tempTemplate.replace(new RegExp('#atributo#', 'gi'), 'TipoProduto');
                    tempTemplate = tempTemplate.replace(new RegExp('#valor#', 'gi'), item);

                    containerHTML.append(tempTemplate);
                }
            }
            else {
                for (var item in data) {
                    tempTemplate = templateRadio;

                    tempTemplate = tempTemplate.replace(new RegExp('#label#', 'gi'), item);
                    tempTemplate = tempTemplate.replace(new RegExp('#id#', 'gi'), metodo + '_' + data[item]);
                    tempTemplate = tempTemplate.replace(new RegExp('#metodo#', 'gi'), metodo);
                    tempTemplate = tempTemplate.replace(new RegExp('#atributo#', 'gi'), 'TipoNegocio');
                    tempTemplate = tempTemplate.replace(new RegExp('#valor#', 'gi'), data[item]);

                    containerHTML.append(tempTemplate);
                }
            }
        },

        // metodo para carregar o filtro do usuario
        // recebendo userId (GUID) e callback
        carregarFiltroUsuario: function(userId, callback) {

            // metodo de ajax jQuery
            $.ajax({
                // metodo do ajax
                type: 'post',

                // url do webservice e metodo
                url: CONFIG.WEBSERVICES.FILTRO.CarregarFiltroUsuario,

                // dados a enviar
                data: userId,

                // tipo dos dados enviados
                dataType: 'json',

                // tipo dos dados recebidos
                contentType: 'application/json',

                // callback de sucesso do ajax
                // recebendo json já parseado como parametro
                success: function(jsonData) {
                    // faz cache do filtro do usuario, fazendo parse dos dados
                    Cache.set("filtroUsuario", JSON.parse(jsonData.d));
                    // escreve dados do usuario passando o filtro e o callback
                    Filtro.escreverFiltroUsuario(cache['filtroUsuario'], callback);
                }
            });
        },

        // metodo para escrever filtro do usuario
        // recebe filtro JSON e o callback
        escreverFiltroUsuario: function(filtro, callback) {

            for (var item in filtro)
                if (filtro[item] != null)
            // se for um slider, seta o valor
                if (item == 'Dormitorios' || item == 'Suites' || item == 'Vagas' || item == 'AreaPrivativa')
                sliders[item].set_value(filtro[item]);
            else {
                if (item == 'PrecoVenda') {
                    if (filtro[item] > 0)
                        sliders[item].set_value(filtro[item] / 1000);
                }
                // senão ativa todos os itens caso seja mais de um
                if (filtro[item].toString().indexOf(',') != -1)
                    for (var k = 0; k < filtro[item].toString().split(',').length; k++)
                    Filtro.ativarItem($('div#filtroBusca a[' + item.toLowerCase() + '=' + filtro[item].split(',')[k] + ']'));
                else {
                    // senão ativa apenas
                    Filtro.ativarItem($('div#filtroBusca a[' + item.toLowerCase() + '=' + filtro[item] + ']'));

                    if (item == 'TipoImovel' && filtro.TipoImovel != undefined)
                        window.TipoImovel = filtro.TipoImovel;

                    if (item == 'TipoUso')
                        Filtro.carregarFiltro('CarregarTiposImovel', { filtroBusca: { TipoUso: $(CONFIG.CONTAINERS.FILTRO.CarregarTiposUso).find('a.ativo').attr('id').split('_')[1]} });

                    if (item == 'Cidade') {
                        
                        Filtro.carregarFiltro('CarregarZonasValor', { filtroBusca: { Cidade: $(CONFIG.CONTAINERS.FILTRO.CarregarCidadesComImoveis).find('a.ativo').attr('id').split('_')[1]} });
                        Filtro.exibirContainer($(CONFIG.CONTAINERS.FILTRO.CarregarZonasValor));
                        

                    }
                    if (item == 'ZonaValor') {                        
                        //$("#selecaoBairros").selectOptions(filtro[item], true);
                        //$('#selecaoBairros option[value=' + filtro[item] + ']').attr("selected", true);

                    }
                }
            }
            if (typeof callback != 'undefined') {
                selecao = $(filtro, selecao)[0];

                filtro.ZonaValor = null;
                filtro.CodFiltroBusca = null;
                filtro.EstagioObra = null;

                // se o item da selecao global for nulo, remove
                for (var item in selecao)
                    if (selecao[item] == null || selecao[item] == '')
                    delete selecao[item];

                // envia busca (callback)
                callback({ filtroBusca: selecao });
            }
        }
    };

    // classe Busca
    // metodos e eventos relacionados ao resultado da busca
    // classe extendida do obj window
    var Busca = window.Busca = {

        // objeto Conteudo
        // metodos e eventos da listagem de conteudo
        Conteudo: {

            // metodo de carregamento da busca
            // recebe o objeto JSON da busca:
            //	{ filtroBusca: String (JSON), userId: String (GUID), sortOrder: String  (ASC ou DESC), sortField: String (null ou nome da coluna), tamanho: int (tamanho da pagina), pagina: int (pagina da paginacao) }
            load: function(params) {
                // não carrega se os filtros ainda não foram carregados
                if (filtroStack < 5)
                    return false;

                // referencia do objeto
                var _this = this,

                // objeto de dados
                    data = {},

                // grafico de loading
                    loader = $('div#divLoadingGrid'),

                // quantidade de itens a exibir na pagina
                    size = parseInt($('select#selRegistrosPagina').val()),

                // mensagem de sucesso/erro
		         spanSuccess = $('span#spnMensagemResultado');

                // transforma array de itens multiplos em string			
                for (var key in params.filtroBusca)
                    if (typeof params.filtroBusca[key] == 'object' && params.filtroBusca[key] != null)
                    params.filtroBusca[key] = params.filtroBusca[key].toString();

                // prepara objeto de parametro do AJAX
                data.filtroBusca = selecao;
                data.userId = $('#codUsuario').val();
                data.sortOrder = 'Ascending';
                data.sortField = null;
                data.tamanho = size;
                data.pagina = 0;
                data.codPortal = $('#codPortal').val();
                // extende objeto default com o passado como parametro
                data = $.extend(data, params);
                data.pagina = data.pagina + 1;

                // exibe mensagem de loading
                spanSuccess.text('Carregando..')

                // seta tamanho da pagina do paginador
                pager.set_pageSize(size);

                // esconde o paginador
                pager.set_visible(false);

                // esconde o grid
                grid.set_visible(false);

                // exibe o grafico de loading
                loader.show();

                // realiza requisicao ajax pelo metodo do jQuery
                $.ajax({
                    // metodo de requisicao
                    type: 'POST',

                    // url do webservice
                    url: CONFIG.WEBSERVICES.CONTEUDO.PesquisarImoveis,

                    // tipo de dados recebidos
                    dataType: 'json',

                    // transforma objeto de parametros em JSON e envia
                    data: JSON.stringify(data),

                    // tipo de dados dos parametros
                    contentType: 'application/json; charset=UTF-8',

                    // callback de sucesso
                    success: function(json) {
                        // escreve conteudo
                        Busca.Conteudo.draw(json);
                    }
                });
            },

            // metodo de escrita da busca
            // recebe json
            draw: function(jsonData) {
                // parseia dados da busca para JS
                var imoveis = JSON.parse(jsonData.d.Imoveis),

                // contagem de itens da busca
                count = jsonData.d.Count,

                // mensagem de sucesso
                spanSuccess = $('span#spnMensagemResultado'),

                // grafico de loading
                loader = $('div#divLoadingGrid');

                // seta numero de itens da paginacao
                pager.set_recordCount(count);

                // limpa todos os markers do mapa
                Busca.Mapa.limparPontos();

                // seta fonte de dados do grid
                grid.set_dataSource(imoveis);

                // executa bind de dados no template
                grid.dataBind();

                // exibe mensagem de sucesso
                spanSuccess.text('Foram encontrados ' + count + ' imóveis');

                // exibe mensagem de erro caso contagem de itens seja 0
                if (count == 0)
                    $('#nenhumRegistro').show();
                else
                    $('#nenhumRegistro').hide();

                // exibe paginacao
                pager.set_visible(true);

                // exibe grid
                grid.set_visible(true);

                // esconde loader
                loader.hide();

                // centraliza mapa na cidade
                var estado = 'SP',
		        cidade = $('#selecaoCidades a.ativo').text(),
		        bairro = $('#selecaoBairros option:selected') != null ? $('#selecaoBairros option:selected').text() : undefined;
                if (cidade == '')
                    cidade = 'São Paulo';

                Busca.Mapa.centralizarMapa(estado, cidade, bairro);
            },

            // evento da paginacao
            // ajax.net
            paginacao: function(sender, e) {
                // seta indice da proxima pagina
                pager.set_pageIndex(e.get_newPageIndex());

                // carrega conteudo da proxima pagina
                Busca.Conteudo.load({ filtroBusca: selecao, pagina: e.get_newPageIndex() });
            },

            // evento de data bound
            // ajax.net
            dataBound: function(sender, e) {
                // linha a ser bindada
                var row = e.get_row(),

                // dados a serem bindados na linha
		    data = row._dataItem,

                // obj jQuery da linha (container)
                    container = $(row.get_container());

                // se o container for fazio ou data nulo, retorna    
                if (container.length == 0 || data == null) return;

                // renderiza template da linha
                Busca.Conteudo.renderTemplate(row, data, container);

                // exibe pontos no mapa
                Busca.Mapa.exibirPontos(data);
            },

            // metodo de reset da paginacao
            // ajax.net
            resetPaginacao: function() {
                // seta paginacao para pagina 0, resetando
                pager.set_pageIndex(0);
            },

            // evento para setar quantidade de itens a serem retornados por pagina
            // recebe dom element select
            setQuantidadeItens: function(element) {
                // quantidade de itens
                var size = $(element).val();

                // reseta paginacao
                Busca.Conteudo.resetPaginacao();

                // carrega conteudo com novo tamanho de pagina
                Busca.Conteudo.load({ tamanho: size });
            },

            // metodo de ordenacao da lista
            // ajax.net
            sort: function(sender, e) {
                // seta coluna a ser ordenada
                grid.set_sortColumn(e.get_sortColumn());

                // seta ordenacao
                grid.set_sortOrder(e.get_sortOrder());

                // reseta paginacao
                Busca.Conteudo.resetPaginacao();

                // serializa o filtro
                Filtro.serializar();
            },

            // metodo de renderizazao de template
            // recebe linha do data bound, dados da linha e o container jQuery
            renderTemplate: function(row, data, container) {
                // se o item for par adiciona classe CSS 'zebraBottom' ao container
                /*     if ((row._rowIndex % 2) == 0)
                container.find('div.itemTemplate').addClass('zebra').children().addClass('zebraBottom');

                // se o item for 0 adiciona classe 'primeiroItem' ao container	
                if (row._rowIndex == 0)
                container.find('div.itemTemplate').addClass('primeiroItem');

                // seta dados no template                
                // foto do produto
                if (data.NomeImagemLista != null)
                container.find('img').attr('src', data.NomeImagemLista).attr('alt', data.Nome);
                else
                container.find('img').attr('src', URL_SEM_FOTO).attr('alt', data.Nome);

                // titulo do produto
                container.find('ul li.titulo h5').text(data.Nome);

                // detalhes do produto
                container.find('ul li.detalhes').text(data.Produto);

                // zona valor
                container.find('p.localizacao').text(data.NomeZonaValor);

                // link de detalhes
                container.find('a').attr('href', '/tabid/' + data.CodTab + '/Default.aspx');
                
                */
                var descricao = "";

                if ((row._rowIndex % 2) == 0) {
                    container.find("div.itemTemplate").addClass("zebra").children().addClass("zebraBottom");
                }
                if (row._rowIndex == 0) {
                    container.find("div.itemTemplate").addClass("primeiroItem");
                }
                if (data.NomeImagemLista != null) {
                    container.find("img").attr("src", data.NomeImagemLista).attr("alt", data.Nome)
                }
                else {
                    if (data.NomeImagemBusca != null) {
                        container.find("img").attr("src", data.NomeImagemBusca).attr("alt", data.Nome)
                    }
                    else {
                        container.find("img").attr("src", URL_SEM_FOTO).attr("alt", data.Nome)
                    }
                }
                //container.find("ul li.titulo h5").text(data.Nome);
                if (data.CodTipoProduto == 1) {
                    descricao = data.Produto
					 container.find("span.localizacao").text(data.Nome);
                }
                else {
                    descricao += Busca.Conteudo.getTipoImovel(data.CodTipoImovel) + ", ";
                    descricao += data.DormitoriosMax + " dormitório" + (data.DormitoriosMax > 1 ? "s" : "") + ", ";
                    descricao += data.SuitesMax + " suíte" + (data.SuitesMax > 1 ? "s" : "") + ", ";
                    descricao += data.AreaMax + " m² Área útil"
					 container.find("span.localizacao").text(data.NomeZonaValor);
                }
				
                container.find("ul li.detalhes").text(descricao);
               
                container.find("a").attr("href", data.UrlAmigavel);
container.find("span.localizacaoCidade").text(data.Cidade);
                container.find("span.localizacaoAbreviacao").text(data.AbreviacaoEstado);
            },

            getTipoImovel: function(index) {
            var data = Cache.get("CarregarTiposImovel");
            if (data != undefined)   
                for (var k = 0; k < data.length; k++) {
                    if (data[k].CodTipoImovel == index) {
                        return data[k].Nome

                    }

                }
            }
        },

        // objeto Mapa
        // metodos e eventos relacionados ao GoogleMap
        Mapa: {
            // metodo de inicializacao do mapa
            iniciar: function() {
                // instancia variavel no objeto window
                window.mapa = '';
                window.geocoder = new GClientGeocoder();

                // verifica compatibilidade do browser
                if (GBrowserIsCompatible()) {
                    // cria nova instancia do mapa no dom element #mapa

                    mapa = new GMap2(document.getElementById('mapa'));

                    // seta centro do mapa pela latitude e longitudo, e seta o nivel de zoom
                    mapa.setCenter(new GLatLng(-46.6658367922849, -23.558544847211), 12); // centraliza em santo andré


                    // adiciona controle simples de mapa
                    mapa.addControl(new GSmallMapControl());
                    mapa.addControl(new GMapTypeControl());
                }
            },

            // metodo para centralizar o mapa na cidade
            // recebe codigo da cidade
            centralizarMapa: function(estado, cidade, bairro) {
                //console.log( bairro ? bairro + ', ' + cidade + '-' + estado : cidade + '-' + estado );

                geocoder.getLatLng(bairro ? bairro + ', ' + cidade + '-' + estado : cidade + '-' + estado, function(ponto) { mapa.setCenter(ponto, 11) });
            },

            // metodo para criar pontos no mapa
            // recebe latitude e longitude
            criarPonto: function(lat, lng) {
                return ponto = new GLatLng(lat, lng)
            },
            criarIcone: function() {
                var icone = new GIcon(G_DEFAULT_ICON);
                icone.image = MAP_ICON;
                icone.iconSize = new GSize(MAP_ICON_WIDTH, MAP_ICON_HEIGHT);
                return icone
            },
            // metodo para templatezar o tooltip
            // recebe dados do databound do imovel
            criarTooltip: function(data) {
                var html = '<div class="tooltipMapa">';

                if (data.NomeImagemLista != null)
                    html += '<img src="' + data.NomeImagemLista + '" alt="" />';

                if (data.Nome != null)
                    html += '<h3>' + data.Nome + '</h3>';

                if (data.Produto != null)
                    html += '<p>' + data.Produto + '</p>';

                if (data.NomeZonaValor != null)
                    html += '<p>' + data.NomeZonaValor + '</p>';

                if (data.CodTab != null)
                    html += '<p><a href="/tabid/' + data.CodTab + '/Default.aspx">Veja mais</a></p>';

                if (html == '<div class="tooltipMapa">')
                    html += '<p>Informações não disponívels.</p>';

                html += '</div>';

                return html;
            },

            // metodo para exibir os pontos no mapa
            // recebe dados do databound do imovel
            exibirPontos: function(data) {
                // cria um marcador no mapa passando como parametro o ponto e o icone
                var marker = new GMarker(Busca.Mapa.criarPonto(data.Latitude, data.Longitude), { icon: Busca.Mapa.criarIcone() });

                // adiciona event listener para click do marcador
                GEvent.addListener(marker, 'click', function() {
                    // abre tooltip com informacoes do imovel
                    marker.openInfoWindowHtml(Busca.Mapa.criarTooltip(data));
                });

                // adiciona o marcador ao mapa
                mapa.addOverlay(marker);
            },

            // evento para excluir marcadores do mapa
            limparPontos: function() {
                // se o mapa existir
                if (mapa != null)
                // limpa os marcadores
                    mapa.clearOverlays();
            }
        }
    };
    var Cache = window.Cache = {
        get: function(metodo) {
            return cache[metodo]
        },
        set: function(metodo, value) {
            cache[metodo] = value
        },
        clear: function(metodo) {
            delete cache[metodo]
        },
        isCached: function(metodo) {
            return typeof cache[metodo] != "undefined"
        }
    };
    /*/// DOCUMENT ONLOAD ///*/
    $(document).ready(function() {
        // instancia stack do load da busca no window
        window.filtroStack = 0;
    });

    /*/// WINDOW ONLOAD ///*/
    $(window).bind('load', function() {
        // instancia eventos aos itens do filtro
        Filtro.selecao();


        // carrega os filtros
        Filtro.carregarFiltro('CarregarTiposProduto', { filtroBusca: {} });
        Filtro.carregarFiltro('CarregarTiposNegocio', { filtroBusca: {} });
        Filtro.carregarFiltro('CarregarTiposUso', { filtroBusca: {} });
        Filtro.carregarFiltro('CarregarCidadesComImoveis', { filtroBusca: {} });

        // inicia o mapa
      Busca.Mapa.iniciar();

        // temporizador do carregamento da busca
        var interval = setInterval(function() {

            // se o stack indicar que todos os filtros já foram carregados, então carrega o filtro do usuario
            if (filtroStack == 5) {
                // passa como parametro o userId (GUID) e o callback                
                Filtro.carregarFiltroUsuario(JSON.stringify({ userId: $('#codUsuario').val() }), Busca.Conteudo.load);

                //limpa temporizador
                clearInterval(interval);
            }
            // valor do temporizador: 100ms
        }, 100);
    });
})()

// funcoes auxiliares para array[]
// retorna bool para item no array
function inArray( valor, arr )
{
    for ( var k = 0; k < arr.length; k++ )
	if ( arr[ k ] == valor )
	    return true;

    return false;
}

// retorna array sem item passado como parametro
function removerArray( valor, arr )
{
    for ( var k = 0; k < arr.length; k++ )
	if ( arr[ k ] == valor )
	    arr.splice( k, 1 );

    return arr;
}
