Печатать книгуПечатать книгу

§ 18. Компоненты для работы с таблицами

Сайт: Профильное обучение
Курс: Информатика. 11 класс (Повышенный уровень)
Книга: § 18. Компоненты для работы с таблицами
Напечатано:: Гость
Дата: Вторник, 7 Май 2024, 07:00

18.1. Компонент StringGrid

Компонент таблица строк — StringGrid предназначен для обработки данных, представленных в табличной форме. На панели компонентов Additional компонент StringGrid изображен в виде , имя объекта StringGrid. Компонент StringGrid, помещенный на форму, получает имя  StringGridN, где N — номер 1, 2, 3… (пример 18.1).

Компонент StringGrid предназначен в первую очередь для отображения в таблице текстовой информации. Однако его можно использовать и для отображения  графической информации. Свойства компонента приведены в примере 18.2. За многие свойства компонента StringGrid отвечает свойство Options (см. Приложение).

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

В компоненте StringGrid реализована адресация каждой отдельной ячейки по ее номеру столбца и строки[1]. Содержимое ячейки (i, j), где i — номер столбца, j — номер строки, имеет вид:

StringGrid1 -> Cells[i][j] 

Номера столбцов и строк начинаются с 0. Столбец и строка с номером нуль по умолчанию принадлежат фиксированной зоне.

В момент выбора пользователем ячейки наступает событие OnSelectCell. В обработчик этого события передаются номера столбца (ACol) и строки (ARow) выделенной ячейки, а также логический параметр CanSelect — допустимость выбора. Параметр CanSelect можно использовать для запрета выделения ячейки, задав его значение false. А параметры ACol и ARow могут использоваться для какой-то реакции программы на выделение пользователя.

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

Этапы выполнения задания

  1. Разместить на форме компонент StringGrid.
  2. Установить у свойства DrawingStyle значение gdsClassic.
  3. Задать цвет для фиксированных и редактируемых ячеек.
  4. В событии OnCreate для формы подписать строки и столбцы.
  5. Написать обработчик события OnSelectCell, в котором необходимо прописывать ее адрес.

Компонент StringGrid можно применять для решения задач, использующих двумерные массивы.

Пример 18.4. Создать проект, в котором будет вычисляться сумма элементов двумерного массива. Элементы массива задаются случайным образом.

Этапы выполнения задания

  1. Разместить на форме компонент StringGrid, а также компоненты: LabeledEdit (2), Label, BitBtn (2), Memo.
  2. Убрать фиксированные строки и столбцы (значения свойств FixedCols и FixedRows равны 0).
  3. Для кнопки BitBtn 2 установить значение Enabled — false.
  4. В событии OnClick для компонента BitBtn1 (Random) изменить размеры таблицы в соответствии с введенными значениями и заполнить ячейки таблицы случайными числами. После заполнения таблицы сделать доступной кнопку Сумма.
  5. В событии OnClick для компонента BitBtn2 (Сумма) посчитать сумму элементов таблицы и вывести ее значение в компонент Label1.

Иногда при работе требуется очистить все ячейки таблицы от текста. Метода, который это делает для таблицы, нет. Можно в цикле обратиться к каждой ячейке и присвоить ей значение пустой строки или использовать метод, который очищает значение столбца:

for (int i = StringGrid1 -> FixedCols; 
    i < StringGrid1 -> ColCount; i++)
    StringGrid1 -> Cols[i] -> Clear();



[1] Обратите внимание на то, что первым указывается номер столбца, а вторым номер строки (по аналогии с адресацией ячеек в Excel)

Пример 18.1. Компонент StringGrid на форме:

Пример 18.2. Свойства компонента StringGrid.

Свойство

Описание

ColCount

Количество столбцов

RowCount

Количество строк

DefaultColWidth

Ширина столбцов

DefaultRowHeight

Высота строк

FixedCols

Количество зафиксированных столбцов слева

FixedRows

Количество зафиксированных строк сверху

GridLineWidth

Толщина линии, ограничивающая ячейки

Options

Определяют группу параметров компонентов

Font

Шрифт отображения содержимого ячеек

Color

Цвет таблицы

FixedColor

Цвет фиксированных ячеек

DrawingStyle

Стиль отображения таблицы

Свойства Color и FixedColor работают, если у свойства DrawingStyle выбрано значение gdsClassic.

При необходимости установки ширины и высоты отдельных столбцов и (или) строк используют свойства:

  • RowHeights - массив, содержащий высоты строк. То есть, например, RowHeights[5] - высота строки с индексом 5.
  • ColWidths - массив, содержащий ширины столбцов. То есть, например, ColWidths[5] - ширина строки с номером 5.

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

Пример 18.3. Форма на этапе проектирования:

Обработчик события OnCreate для формы.

void __fastcall TForm1::
FormCreate(TObject *Sender)

{

  for(int i = 1;

  i < StringGrid1 -> ColCount; i++)

    StringGrid1 -> Cells[i][0] =

    "столбец " + IntToStr(i);

  for(int i = 1;

  i < StringGrid1 -> RowCount; i++)

    StringGrid1 -> Cells[0][i] =

    "строка " + IntToStr(i);

}

Обработчик события OnSelectCell для таблицы.

void __fastcall TForm1::

StringGrid1SelectCell(TObject *Sender,

int ACol, int ARow, bool &CanSelect)

{

  StringGrid1 -> Cells[ACol][ARow] =

  IntToStr(ACol) + ";" + IntToStr(ARow);

}

Работающее приложение:

Пример 18.4. Форма на этапе проектирования:

Обработчик события OnClick для кнопки BitBtn1.

void __fastcall TForm1::BitBtn1Click
               (TObject *Sender)

{

  n = StrToInt(LabeledEdit1 -> Text);

  m = StrToInt(LabeledEdit2 -> Text);

  StringGrid1 -> RowCount = n;

  StringGrid1 -> ColCount = m;

  for (int i = 0; i < m; i++)

  for (int j = 0; j < n; j++)

    StringGrid1 -> Cells[i][j] =

      rand() % 20;

  BitBtn2 -> Enabled = true;

}

Обработчик события OnClick для кнопки BitBtn2.

void __fastcall TForm1::

BitBtn2Click(TObject *Sender)

{

  int s = 0;

  for (int i = 0; i < m; i++)

    for (int j = 0; j < n; j++)

      s += StrToInt(StringGrid1 

          -> Cells[i][j]);

  Label1 -> Caption = "Sum = " + IntToStr(s);

}

Работающее приложение:

18.2. Компонент DrawGrid

Компонент DrawGrid используется для создания таблицы, которая может содержать графические изображения. На панели компонентов Additional компонент DrawGrid изображен в виде , имя объекта DrawGrid. Компонент DrawGrid, помещенный на форму, получает имя  DrawGridN, где N — номер 1, 2, 3… (пример 18.5).

Этот компонент подобен компоненту StringGrid, который является наследником от DrawGrid. В DrawGrid присутствуют все свойства, методы, события компонента StringGrid, кроме относящихся к тексту, т.е. кроме свойств Cells, Cols, Rows.

Компонент DrawGrid (также StringGrid) имеет канву, на которой можно размещать изображения. Для занесения изображений в ячейки DrawGrid используют обработчик событий OnDrawCell. Это событие наступает для каждой ячейки таблицы в момент ее перерисовки. Размещая в обработчике события OnDrawCell программный код, можно раскрашивать ячейки, выводить рисунки, и делать текстовые надписи. Таблица сама постоянно вызывает это событие для того, чтобы отрисовать свои ячейки. Прорисовать изображение можно, используя методы канвы StratchDraw или CopyRect.

Обработчик OnDrawCell имеет параметры (пример 18.6).

Пример 18.7. Создать проект, в котором при выборе ячейки таблицы, будет либо закрашиваться ячейка, либо прорисовываться картинка. Если сумма номера строки и номера столбца нечетная, то происходит закраска ячейка, иначе прорисовывается картинка.

Этапы выполнения задания

  1. Разместить на форме компонент DrawGrid.
  2. Убрать фиксированные строки и столбцы.
  3. Установить для таблицы 5 строк и 5 столбцов.
  4. Установить ширину и высоту столбца равной 60.
  5. В событии OnCreate для формы загрузить рисунок в битовый образ.
  6. Написать обработчик события OnDrawCell, в котором зарисовывать ячейки.

Если свойство DefaultDrawing компонента DrawGrid имеет значение true (установлено по умолчанию), то зарисовываться будут только выделенные ячейки таблицы. Как только выделение изменится ячейка становится закрашенной тем цветом, который установлен по умолчанию. Если для свойства DefaultDrawing установить значение false, то после смены выделенной ячейки раскраска предыдущих ячеек не меняется.

Компонент DrawGrid удобно использовать для создания игр на клеточном поле. Для программирования игры понадобится матрица состояния игры. В такой матрице будет храниться обстановка игры на текущем ходу. После выполнения хода обстановка меняется, соответствующие изменения записываются в матрицу состояния и происходит обновление компонента DrawGrid. Матрица состояния игры может использоваться для сохранения игры и последующей ее загрузки.

Пример 18.8. Подготовить поле игры в крестики-нолики для двух игроков.

Этапы выполнения задания

  1. Разместить на форме компонент DrawGrid и кнопку.
  2. Убрать фиксированные строки и столбцы.
  3. Количество строк и столбцов равно 3.
  4. Для хранения матрицы состояния игры описать двумерный массив pole из 3 строк и 3 столбцов. Состояние клетки будем описывать одним из трех значений: 0 — клетка пуста, 1 — в клетке крестик, 2 — в клетке нолик.
  5. Написать обработчик события OnCreat для формы, в котором следует загрузить два битовых образа — рисунки для крестика и нолика.
  6. Написать обработчик события OnSelectCell, в котором необходимо изменить значение элемента массива pole для выбранной клетки. Для определения того, что рисовать в клетке на текущем шаге будем использовать символьную переменную znak, которая будет менять свое значение после каждого хода. Вначале znak = 'X';
  7. Написать обработчик события OnDrawCell, в котором нужно рисовать в ячейке картинку, соответствующую матрице состояния.
  8. Написать обработчик события OnClick для кнопки, в котором необходимо обнулить массив. После обнуления массива перерисовать таблицу на форме. Команда DrawGrid1 -> Refresh(); вызывает обработчик события OnDrawCell.

Компонент StringGrid обладает существенно большими возможностями, чем DrawGrid, поскольку он может хранить в ячейках и изображения, и тексты. Если необходимо внести текст в какие-то ячейки DrawGrid, то потребуется  использовать методы вывода текста на канву, что не всегда удобно.

Пример 18.5. Компонент DrawGrid на форме:

Пример 18.6. Параметры обработчика OnDrawCell:

  • ACol, ARow — индексы столбца и строки;
  • Rect — прямоугольник в рамках ячейки, заданной индексами ACol и ARow;
  • State — состояние ячейки:

-  gdSelected — ячейка выделена;
- gdFocused — ячейка имеет фокус ввода;
- gdFixed — ячейка относится к фиксированной строке или столбцу.

Пример 18.7. Форма на этапе проектирования:

Обработчик события OnCreate для формы.

void __fastcall TForm1::

FormCreate(TObject *Sender)

{

  ris -> LoadFromFile("fly.bmp");

}

Обработчик события OnSelectCell для таблицы.

void __fastcall TForm1::
DrawGrid1DrawCell(TObject *Sender,

int ACol, int ARow, TRect &Rect, 
TGridDrawState State)

{

  if (State.Contains(gdSelected)) {

    if ((ACol + ARow) % 2) {

      DrawGrid1 -> Canvas -> Brush

       -> Color = clSkyBlue;

      DrawGrid1 -> Canvas ->

       FillRect(Rect);

    }

    else

      DrawGrid1 -> Canvas ->

      StretchDraw(Rect, ris);

  }

}

Работающее приложение:

Пример 18.8. Форма на этапе проектирования:

Обработчик события OnCreate для формы.

void __fastcall TForm1::

FormCreate(TObject *Sender) 

{

  znak = 'X';

  kr -> LoadFromFile("k.bmp");

  nl -> LoadFromFile("n.bmp");

}

Обработчик события OnSelectCell для таблицы.

void __fastcall TForm1::

DrawGrid1SelectCell(TObject 
*Sender, int ACol,
int ARow,  bool &CanSelect)

{

  if (pole[ACol][ARow] == 0)

    if (znak == 'X') {

      pole[ACol][ARow] = 1;

      znak = 'O';

    }

    else {

      pole[ACol][ARow] = 2;

      znak = 'X';

    }

}

Обработчик события OnDrawCell для таблицы.

void __fastcall TForm1::

DrawGrid1DrawCell(TObject 

*Sender, int ACol, int ARow,

 TRect &Rect, TGridDrawState State) 

{

  switch (pole[ACol][ARow]) {

    case 1: {

      DrawGrid1 -> Canvas -> 

      StretchDraw(Rect, kr);

      break;

    }

    case 2: {

      DrawGrid1 -> Canvas -> 

      StretchDraw(Rect, nl);

      break;

    }

  }

}

Обработчик события OnClick для кнопки.

void __fastcall TForm1::

BitBtn1Click(TObject *Sender)

{

  for (int i = 0; i < 3; i++)

    for (int j = 0; j < 3; j++)

      pole[i][j] = 0;

  DrawGrid1 -> Refresh();

}

Работающее приложение:

Вопросы к параграфу

1. Какой компонент используется для работы с данными, представленными в виде таблицы?

2. Какой обработчик событий используется для выделения ячейки таблицы?

3. Какой компонент используется для представления графических данных в табличной форме?

4. Какой обработчик используется для прорисовки ячейки таблицы?

5. С помощью какой команды можно вызвать обработчик события OnDrawCell?


Упражнения

1. Создайте проект для решения задачи. Дан двумерный массив А[m][n]. Посчитать сумму.

    1. элементов, у которых сумма номера строки и номера столбца равна числу x. Число x вводится;
    2. элементов, которые меньше номера своей строки;
    3. элементов, которые больше номера своего столбца;
    4. элементов, у которых модуль разности номера строки и номера столбца равен числу x (добавить поле для ввода числа x);
    5. элементов, которые расположены на главной и побочной диагоналях.

2. Объедините решение всех задач из упражнения 1 в один проект. Выбор номера задачи осуществлять из выпадающего списка. При выборе номера задачи, выводить в Memo ее условие.

Создайте проект для решения задачи. Дан двумерный массив А[m][n]. Вывести:

  1. номер столбца, сумма элементов которого максимальна;
  2. номер строки, сумма элементов которой минимальна;
  3. номера строк, в которых есть элементы, равные максимальному элементу таблицы.
  4. номера столбцов, в которых есть элементы, равные минимальному элементу таблицы.
  5. номера строк, в которых есть равные элементы;
  6. номера столбцов, в которых все элементы различны;
  7. номера строк, суммы элементов в которых равны между собой.

3. Создайте проект, в котором можно строить диаграммы по данным в таблице. Для построения диаграмм необхрдимо использовать компонент Chart.

4. Допишите в пример 18.7 проверку выигрыша на текущем ходе. В случае выигрыша выводить соответствующее сообщение.

5*.  Добавьте в проект примера из 18.7 возможность игры с компьютером. Компьютер играет ноликами.

6. Создайте проект, в котором можно подготовить поле для игры «Морской бой». Созданное поле сохранять в текстовый файл.