private void _Btn_Buscar_Click(object sender, EventArgs e)
        {
            if (BotonBuscarClick != null)
            {
                Cursor = Cursors.WaitCursor;

                FiltroCombo oArregloFiltro = (FiltroCombo)_Cmb_FiltrarPor.SelectedItem;

                BotonBuscarClick(oArregloFiltro.Nombre, _Txt_Buscar);

                agregarFiltroGrid(oArregloFiltro, _Txt_Buscar.Text, _Txt_Buscar.Tag.ToString());

                if ((_Txt_Buscar.Text != "") && (_Txt_Buscar.Tag != ""))
                {
                    _Txt_Buscar.Text = "";
                    _Txt_Buscar.Tag  = "";
                }

                Cursor = Cursors.Default;

                ordenarFiltros();

                cambiarAspectoGrid();
            }
        }
        /// <summary>Agrega un filtro al combo de filtrar por.</summary>
        /// <param name="pElemento">Objeto con los datos del combo.</param>
        public void agregarFiltrarPor(FiltroCombo pElemento)
        {
            gListaFiltros.Add(pElemento);

            _Cmb_FiltrarPor.DataSource    = null;
            _Cmb_FiltrarPor.DataSource    = gListaFiltros;
            _Cmb_FiltrarPor.DisplayMember = "TituloFiltrarPor";
            _Cmb_FiltrarPor.ValueMember   = "Nombre";
        }
        /// <summary>Agregar una fila al Grid.</summary>
        /// <param name="pFiltroSeleccionado">Datos del filtro seleccionado en el combo filtrar por.</param>
        /// <param name="pDescripcion">Descripción del filtro.</param>
        /// <param name="pValor">Valor del filtro.</param>
        private void agregarFiltroGrid(FiltroCombo pFiltroSeleccionado, string pDescripcion, string pValor)
        {
            _Dtg_Filtros.DataSource = null;

            /*
             *  Aqui se hace lo siguiente:
             *
             *  1. Buscamos el filtro, y si existe en el grid, lo actualizamos y nos salimos de la rutina.
             *  2. De lo contrario, un filtro nuevo se agrega al grid.
             *  3. Finalmente se muestra el encabezado si es el primer filtro en el grid.
             */

            for (int iIndice = 0; iIndice < gListaFiltrosGrid.Count; iIndice++)
            {
                if (gListaFiltrosGrid[iIndice].Nombre == pFiltroSeleccionado.Nombre)
                {
                    gListaFiltrosGrid[iIndice].Descripcion = pDescripcion;
                    gListaFiltrosGrid[iIndice].Valor       = pValor;

                    _Dtg_Filtros.DataSource = gListaFiltrosGrid;

                    return;
                }
            }

            gListaFiltrosGrid.Add(new FiltroGrid
            {
                Tipo        = pFiltroSeleccionado.Tipo,
                Titulo      = pFiltroSeleccionado.TituloGrid,
                Nombre      = pFiltroSeleccionado.Nombre,
                Valor       = pValor,
                Descripcion = pDescripcion
            });

            _Dtg_Filtros.DataSource = gListaFiltrosGrid;

            if (_Dtg_Filtros.Rows.Count > 0)
            {
                _Dtg_Filtros.ColumnHeadersVisible = true;
            }
        }
        private void _Txt_Texto_TextChanged(object sender, EventArgs e)
        {
            if (_Txt_Texto.Text != "")
            {
                agregarFiltroGrid((FiltroCombo)_Cmb_FiltrarPor.SelectedItem, _Txt_Texto.Text, _Txt_Texto.Text);

                cambiarAspectoGrid();
            }
            else
            {
                // Si el TextBox queda vacío, se remueve el filtro del DataGridView.

                FiltroCombo oArregloFiltro = (FiltroCombo)_Cmb_FiltrarPor.SelectedItem;

                IEnumerable <FiltroGrid> oDatos = from oFiltro in gListaFiltrosGrid
                                                  where (oFiltro.Tipo != oArregloFiltro.Tipo)
                                                  select oFiltro;

                gListaFiltrosGrid = oDatos.ToList();

                _Dtg_Filtros.DataSource = null;

                if (gListaFiltrosGrid.Count == 0)
                {
                    _Dtg_Filtros.ColumnHeadersVisible = false;
                }
                else
                {
                    _Dtg_Filtros.DataSource = gListaFiltrosGrid;

                    ordenarFiltros();

                    cambiarAspectoGrid();
                }
            }
        }
        private void _Btn_Agregar_Click(object sender, EventArgs e)
        {
            IEnumerable <FiltroGrid> oIndice, oExiste;

            FiltroCombo oFiltroCombo = (FiltroCombo)_Cmb_FiltrarPor.SelectedItem;

            _Cls_ArrayList oArreglo = (_Cls_ArrayList)_Cmb_Compuesto.SelectedItem;

            /*
             *  Aqui se hace lo siguiente:
             *
             *  1. Aqui se evita que se agregue el texto "Seleccionar..." en el grid.
             *  2. Verificamos que el filtro existe en el grid, si existe manda una advertencia.
             *  3. De lo contrario, se agrega al grid el filtro.
             */

            if (oArreglo.Value == "SEL")
            {
                return;
            }

            oExiste = from oFiltro in gListaFiltrosGrid where
                      (
                (oFiltro.Valor == oArreglo.Value) &&
                (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoCompuesto)
                      )
                      select oFiltro;

            if (oExiste.ToList().Count == 1)
            {
                MessageBox.Show("Ya existe un filtro con ese valor.", "Advertencia", MessageBoxButtons.OK, MessageBoxIcon.Information);

                return;
            }

            Cursor = Cursors.WaitCursor;

            _Dtg_Filtros.DataSource = null;

            if ((gSeleccionarTodos) && (oArreglo.Value == "SELT"))
            {
                _Cls_ArrayList oDatos;

                for (int iIndice = 2; iIndice < _Cmb_Compuesto.Items.Count; iIndice++)
                {
                    /*
                     *  Por cada valor en el combo _Cmb_Compuesto:
                     *
                     *  1. Se genera un índice para el filtro, ejemplo: Proveedor #1, Proveedor #2, Proveedor #3, etc.
                     *  2. Se agregan los datos del combo al grid.
                     */

                    oDatos = (_Cls_ArrayList)_Cmb_Compuesto.Items[iIndice];

                    oIndice = from oFiltro in gListaFiltrosGrid
                              where
                              (
                        (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoCompuesto) &&
                        (oFiltro.Nombre == oFiltroCombo.Nombre)
                              )
                              select oFiltro;

                    oExiste = from oFiltro in gListaFiltrosGrid
                              where
                              (
                        (oFiltro.Valor == oDatos.Value) &&
                        (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoCompuesto)
                              )
                              select oFiltro;

                    if (oExiste.ToList().Count == 0)
                    {
                        gListaFiltrosGrid.Add(new FiltroGrid
                        {
                            Tipo        = oFiltroCombo.Tipo,
                            Titulo      = oFiltroCombo.TituloGrid.Replace(":", " #" + (oIndice.ToList().Count + 1) + ":"),
                            Nombre      = oFiltroCombo.Nombre,
                            Valor       = oDatos.Value,
                            Descripcion = oDatos.Display
                        });
                    }
                }
            }
            else
            {
                /*
                 *  Por cada valor en el combo _Cmb_Compuesto:
                 *
                 *  1. Se genera un índice para el filtro, ejemplo: Proveedor #1, Proveedor #2, Proveedor #3, etc.
                 *  2. Se agregan los datos del combo al grid.
                 */

                oIndice = from oFiltro in gListaFiltrosGrid where
                          (
                    (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoCompuesto) &&
                    (oFiltro.Nombre == oFiltroCombo.Nombre)
                          )
                          select oFiltro;

                oExiste = from oFiltro in gListaFiltrosGrid where
                          (
                    (oFiltro.Valor == oArreglo.Value) &&
                    (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoCompuesto)
                          )
                          select oFiltro;

                if (oExiste.ToList().Count == 0)
                {
                    gListaFiltrosGrid.Add(new FiltroGrid
                    {
                        Tipo        = oFiltroCombo.Tipo,
                        Titulo      = oFiltroCombo.TituloGrid.Replace(":", " #" + (oIndice.ToList().Count + 1) + ":"),
                        Nombre      = oFiltroCombo.Nombre,
                        Valor       = oArreglo.Value,
                        Descripcion = oArreglo.Display
                    });
                }
            }

            _Dtg_Filtros.DataSource = gListaFiltrosGrid;

            if (_Dtg_Filtros.Rows.Count > 0)
            {
                _Dtg_Filtros.ColumnHeadersVisible = true;
            }

            ordenarFiltros();

            cambiarAspectoGrid();

            Cursor = Cursors.Default;
        }
        private void _Btn_Remover_Click(object sender, EventArgs e)
        {
            FiltroCombo oArregloFiltro = (FiltroCombo)_Cmb_FiltrarPor.SelectedItem;

            IEnumerable <FiltroGrid> oFiltros = null, oFiltrosSeleccionados = null, oFiltrosNoSeleccionados = null, oFiltrosFechasAño = null;

            /*
             *  Aqui se hace lo siguiente:
             *
             *  1. Se extraen los filtros que no están seleccionados en el grid.
             *  2. Se verifica si en los filtros seleccionados exista alguno por fechas o mes y se eliminan ambos (Desde - Hasta) o (Año - Mes).
             *  3. Se actualiza el grid de los filtros.
             */

            oFiltrosNoSeleccionados = from oFiltro in gListaFiltrosGrid
                                      where (oFiltro.Seleccionar == false)
                                      select oFiltro;

            //  Aquí se comprueba si los filtros son de fecha o mes para eliminar el par, para la fecha (Desde - Hasta) y para el año (Año - Mes).

            oFiltrosFechasAño = from oFiltro in oFiltrosNoSeleccionados.ToList() where
                                (
                (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoFecha) ||
                (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoAñoMes)
                                )
                                select oFiltro;

            if (oFiltrosFechasAño.ToList().Count == 1)
            {
                oFiltros = from oFiltro in oFiltrosNoSeleccionados.ToList() where
                           (
                    (oFiltro.Tipo != _Enu_MultifiltroTipos.MultifiltroTipoFecha) &&
                    (oFiltro.Tipo != _Enu_MultifiltroTipos.MultifiltroTipoAñoMes)
                           )
                           select oFiltro;
            }
            else
            {
                oFiltros = oFiltrosNoSeleccionados.ToList();
            }

            // Se actualizan los datos.

            gListaFiltrosGrid = oFiltros.ToList();

            _Dtg_Filtros.DataSource = null;

            if (gListaFiltrosGrid.Count == 0)
            {
                _Dtg_Filtros.ColumnHeadersVisible = false;
            }
            else
            {
                _Dtg_Filtros.DataSource = gListaFiltrosGrid;

                ordenarFiltros();

                cambiarAspectoGrid();

                organizarTituloFiltro();

                // Las siguientes líneas son para inicializar los combos.

                if (_Cmb_FiltrarPor.Items.Count > 0)
                {
                    _Cmb_FiltrarPor.SelectedIndex = 0;

                    if (FiltroSeleccionado != null)
                    {
                        FiltroSeleccionado((FiltroCombo)_Cmb_FiltrarPor.SelectedItem, gListaFiltrosGrid);
                    }
                }

                if (_Cmb_Estado.Items.Count > 0)
                {
                    _Cmb_Estado.SelectedIndex = 0;
                }

                if (_Cmb_Compuesto.Items.Count > 0)
                {
                    _Cmb_Compuesto.SelectedIndex = 0;
                }
            }

            if (FiltroSeleccionado != null)
            {
                FiltroSeleccionado((FiltroCombo)_Cmb_FiltrarPor.SelectedItem, gListaFiltrosGrid);
            }
        }
        /// <summary>Muestra el filtro.</summary>
        /// <param name="pTipo">Tipo de control que debe mostrarse.</param>
        public void mostrarFiltro(_Enu_MultifiltroTipos pTipo)
        {
            ocultar();

            FiltroCombo oArregloFiltro = (FiltroCombo)_Cmb_FiltrarPor.SelectedItem;

            IEnumerable <FiltroGrid> oFiltros;

            switch (pTipo)
            {
            case _Enu_MultifiltroTipos.MultifiltroTipoCombo:

                _Lbl_Estado.Text    = oArregloFiltro.TituloEtiqueta;
                _Lbl_Estado.Visible = true;
                _Cmb_Estado.Visible = true;

                break;

            case _Enu_MultifiltroTipos.MultifiltroTipoBuscar:

                _Lbl_Estado.Text    = oArregloFiltro.TituloEtiqueta;
                _Lbl_Estado.Visible = true;
                _Txt_Buscar.Text    = "";
                _Txt_Buscar.Visible = true;
                _Btn_Buscar.Visible = true;

                break;

            case _Enu_MultifiltroTipos.MultifiltroTipoCaja:

                _Lbl_Estado.Text    = oArregloFiltro.TituloEtiqueta;
                _Lbl_Estado.Visible = true;
                _Txt_Texto.Visible  = true;
                _Txt_Texto.Focus();

                break;

            case _Enu_MultifiltroTipos.MultifiltroTipoAñoMes:

                oFiltros = from oFiltro in gListaFiltrosGrid
                           where (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoAñoMes)
                           select oFiltro;

                if (oFiltros.ToList().Count == 0)
                {
                    _Cls_ArrayList oAño = (_Cls_ArrayList)_Cmb_Año.SelectedItem;
                    _Cls_ArrayList oMes = (_Cls_ArrayList)_Cmb_Mes.SelectedItem;

                    if (oMes == null)
                    {
                        return;
                    }

                    gListaFiltrosGrid.Add(new FiltroGrid
                    {
                        Tipo        = _Enu_MultifiltroTipos.MultifiltroTipoAñoMes,
                        Titulo      = "Año:",
                        Nombre      = "cano",
                        Valor       = oAño.Value,
                        Descripcion = oAño.Display
                    });

                    gListaFiltrosGrid.Add(new FiltroGrid
                    {
                        Tipo        = _Enu_MultifiltroTipos.MultifiltroTipoAñoMes,
                        Titulo      = "Mes:",
                        Nombre      = "cmes",
                        Valor       = oMes.Value,
                        Descripcion = oMes.Display
                    });
                }

                _Dtg_Filtros.DataSource = null;

                // Aqui se elimina el filtro de fecha (Desde - Hasta) en el caso de que esté en el grid.

                oFiltros = from oFiltro in gListaFiltrosGrid
                           where (oFiltro.Tipo != _Enu_MultifiltroTipos.MultifiltroTipoFecha)
                           select oFiltro;

                gListaFiltrosGrid = oFiltros.ToList();

                _Dtg_Filtros.DataSource = gListaFiltrosGrid;

                if (_Dtg_Filtros.Rows.Count > 0)
                {
                    _Dtg_Filtros.ColumnHeadersVisible = true;
                }

                cambiarAspectoGrid();

                _Lbl_Año.Visible = true;
                _Cmb_Año.Visible = true;
                _Lbl_Mes.Visible = true;
                _Cmb_Mes.Visible = true;

                break;

            case _Enu_MultifiltroTipos.MultifiltroTipoFecha:

                _Dtp_Desde.Value = DateTime.Now;
                _Dtp_Hasta.Value = DateTime.Now;

                oFiltros = from oFiltro in gListaFiltrosGrid
                           where (oFiltro.Tipo == _Enu_MultifiltroTipos.MultifiltroTipoFecha)
                           select oFiltro;

                if (oFiltros.ToList().Count == 0)
                {
                    gListaFiltrosGrid.Add(new FiltroGrid
                    {
                        Tipo        = _Enu_MultifiltroTipos.MultifiltroTipoFecha,
                        Titulo      = "Desde:",
                        Nombre      = "cdesde",
                        Valor       = _Dtp_Desde.Value.ToShortDateString(),
                        Descripcion = _Dtp_Desde.Value.ToShortDateString()
                    });

                    gListaFiltrosGrid.Add(new FiltroGrid
                    {
                        Tipo        = _Enu_MultifiltroTipos.MultifiltroTipoFecha,
                        Titulo      = "Hasta:",
                        Nombre      = "chasta",
                        Valor       = _Dtp_Hasta.Value.ToShortDateString(),
                        Descripcion = _Dtp_Hasta.Value.ToShortDateString()
                    });
                }

                _Dtg_Filtros.DataSource = null;

                // Aqui se elimina el filtro de año y mes en el caso de que esté en el grid.

                oFiltros = from oFiltro in gListaFiltrosGrid
                           where (oFiltro.Tipo != _Enu_MultifiltroTipos.MultifiltroTipoAñoMes)
                           select oFiltro;

                gListaFiltrosGrid = oFiltros.ToList();

                _Dtg_Filtros.DataSource = gListaFiltrosGrid;

                if (_Dtg_Filtros.Rows.Count > 0)
                {
                    _Dtg_Filtros.ColumnHeadersVisible = true;
                }

                cambiarAspectoGrid();

                _Lbl_Desde.Visible = true;
                _Dtp_Desde.Visible = true;
                _Lbl_Hasta.Visible = true;
                _Dtp_Hasta.Visible = true;

                break;

            case _Enu_MultifiltroTipos.MultifiltroTipoCompuesto:

                _Lbl_Estado.Text       = oArregloFiltro.TituloEtiqueta;
                _Lbl_Estado.Visible    = true;
                _Cmb_Compuesto.Visible = true;
                _Btn_Agregar.Visible   = true;

                break;
            }
        }