Введение в ADO.NET. Источник данных - XML-файл. Отображение данных связанной таблицы, страница 14

  }

  bool FindNext(int row, int col)

  {

    bool bFound = false;

    for (int i = row; findWhat.Length > 0 && !bFound; )    // Цикл поиска

    {

      // Здесь ваш код

    }

    return bFound;

  }

¨  Ввести реакцию на событие CellEnter (вход фокуса) компонента DataGridView и корректировать в ней флаг bFindNext, а также activeCell — ссылку на активную в данный момент ячейку.

  void grid_CellEnter(object sender, DataGridViewCellEventArgs e)

  {

    sNotFound.Visible = false;

    if (e.RowIndex != -1 && e.ColumnIndex != -1)

    {

      activeCell = (DataGridViewCell)studsGrid.Rows[e.RowIndex].Cells[e.ColumnIndex];

      if (activeCell != foundCell)

        bFindNext = false;

    }

  }

Проверка показывает удовлетворительное поведение приложения в режиме поиска, но здесь, конечно, остались подводные камни. Чтобы увидеть их, надо связать DataGridView с реальной таблицей базы данных, которая может содержать тысячи строк.

Поиск в произвольной таблице

Пользователь должен иметь возможность искать и во второй таблице (экзаменов). Скорректируйте алгоритм так, чтобы пользователь мог искать текст как в ячейках первого, так и второго DataGriView. Для этого можно ввести ссылку на активный DataGriView, (назовите ее activeGrid), и корректировать ее значение в реакции на событие CellEnter (activeGrid = sender as DataGridView;). Реакция уже существует, но ее надо сделать общей для обоих DataGriView. Затем вместо ссылки studsGrid используйте, где это необходимо, ссылку activeGrid.

Отбор данных из DataTable и отображение их в ListView

Рассмотрим вариант поиска в таблице DataTable (то есть, в памяти) и одновременного отображения всех данных, удовлетворяющих критерию поиска, в списке ListView. Этот список покажем в отдельном окне. Данные получим с помощью запроса к таблице DataTable, Запрос произведем путем вызова метода Select, как было показано ранее.

Множество строк таблицы DataRow[], удовлетворяющее критерию отбора и возвращаемое методом Select, преобразуем в текстовые строки и поместим их в стандартный элемент управления, управляемый классом ListView. Сам список (ListView) поместим в отдельную, временную форму, которая должна появиться рядом с главным окном приложения.

¨  В режиме дизайна фомы добавьте новую кнопку c именем btnFindList и текстом Find List.

¨  В класс формы главного окна введите новые переменные

  Form formFound;

  bool bSearchChanged;

  DataGridView searchGrid;

  DataTable activeTable;

  string searchColumnName, searchControl;

¨  Проведите инициализацию переменных в конструкторе класса.

  Thread.CurrentThread.CurrentCulture = new CultureInfo(1033);

  bFindNext = bSearchChanged = false;

  foundCell = null;

  activeGrid = studsGrid;

  btnFindList.Enabled = Trim(comboFind.Text) != "";

Культуру я заменил на "en-US", так как SQL-запрос не желает работать с запятыми, автоматически внесенными русской культурой в колонку со средним баллом. Неприятность возникает при поиске именно в этой колонке.

¨  Добавьте метод, который создает вспомогательную форму, вычисляет ее координаты, вставляет в коллекцию дочерних элементов список с результатами поиска и отображает на экране.

  void ShowSearchResults(Control control, string text)

  {

    if (formFound != null)

      formFound.Dispose();

    formFound = new Form();

    // Здесь ваш код Создайте метку с текстом "Ищу то-то в такой-то таблице

    // Здесь ваш код Добавьте метку в форму

    formFound.Text = "Search results";

    formFound.MinimizeBox = false;

    formFound.MaximizeBox = false;

    formFound.Owner = this;

    formFound.Width = Math.Max(msg.Width, control.Width) + 14;

    formFound.Height = msg.Height + control.Height + 38;

    control.Location = new Point(3, msg.Height + 5);

    formFound.Controls.Add(control);

    formFound.Visible = true;

    formFound.Location = new Point(Location.X + Width - 60, Location.Y + 100);

  }

¨  В метод toolStrip_ItemClicked добавьте ветвь обработки события нажатия кнопки btnFindList и создайте метод, FindAndShowList, реагирующий на это событие.