Лекція 2. Семестр 2. Приклади стандартних дій в Ексель

 

 

 

 

 

         В даній лекції будуть винесені в окремі функції основні операції, які потрібні при переносі даних в ексель. Для зручності можна їх винести в окремий клас, можна їх використовувати як окремі функції в просторі імен вашого додатку. В будь-якому разі метою даної лекції буде висвітлення лише методів роботи з екселем, а не якогось конкретного механізму внутрішньої взаємодії компонентів всередині додатку.

Отже для початку потрібно завантажити ексель. Припустимо, що всі потрібні модулі роботи екселю підключені і ми можемо вже викликати потрібні нам функції. Перше що нам потрібно це відкрити та закрити ексель.

Для збереження зв’язків з самим екселем та робочою сторінкою, будемо використовувати дві такі змінні.

public excel.Application excelapp; //змінна для збереження зв"язку із екселем

public excel.Worksheet sheet; //змінна для посилання на робочий лист куди будуть виводитися дані

 

Процедура завантаження та ініціалізації з’єднання з екселем може виглядати так:

public void RunExcel(string n = "Немає імені",bool visible=true) //Завантажує ексель

    //де n - задає назву листа

    //visible - показувати чи ні ексель на екрані

 {

  excelapp = new excel.Application();//створюємо зв"язок з екселем і поміщаємо його в excelapp

  excelapp.Visible = visible; //показуємо ексель на екрані, якщо потрібно

  excelapp.SheetsInNewWorkbook = 1; // Кількість сторінок які будуть у книзі

  excelapp.Workbooks.Add(Type.Missing); //Створюємо нову книгу

  sheet = excelapp.Workbooks[1].Worksheets[1]; //Зв"язуємо лист робочої книги і змінну sheet

  sheet.Name = n;// Присвоюємо назву

 }

Показувати ексель на екрані потрібно лише в самому кінці, так як, кожен крок (перенос даних в клітинку, форматування і тд) буде відображатися на екрані, а на це буде затрачатися процесорний час, за рахунок чого Ваша інформаційна система буде формувати звіт значно довше. Але в навчальних цілях ми будемо відображати його з самого початку, щоб ви «наочно» могли спостерігати сам процес.

Процедура закриття нам потрібна лише для «екстрених» випадків, наприклад, коли в блоці була перехоплена помилка і існує вірогідність, що дані не були передані повністю, і, щоб не відображати користувачу.

public void QuitExcel() //Екстренний вихід з екселю, наприклад, кщо трапилась помилка

 {

  if (excelapp != null)//якщо ексель був запущений

   {

    excelapp.DisplayAlerts = false;//Забороняємо показувати повідомлення користувачу

    excelapp.Quit();//Виходимо з екселю

   }

  sheet = null;//Присвоюємо порожнє значення

  excelapp = null;//листу і екселю (знищуємо)

 }

Для того, щоб мати змогу перенести в ексель хоча б що-небудь потрібно перейти від числового індексу клітинки (який використовується в c#) до буквенно-числового (який використовує ексель). Функція може мати вигляд:

public string ConvertRange(int x, int y)// перетворює числову адресу клітинки в формат виду "А1"

 {

  string n = "";//тут буде міститися перетворена адреса

  string sym = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";//Літери англійського алфавіту, використовуються для першої координати

  int symc = 26;//Кількість літер

  if (x / symc == 0)//якщо 0, тоді терша координата буде з однієї літери

   { n = sym[x].ToString(); }//записуємо відповідний індекс літри, як першу координату

  else //якщо кордината записується двома літерами

   { n = sym[x / symc].ToString() + sym[x % symc]; }//додаємо дві літери - перша відділення націло, друга остача від ділення

  n = n + y.ToString();//додаємо другу координату

  return n;//повертаємо перетворені координати

 }

 

Тепер ми можемо перейти до вставки тексту в клітинку, процедура може мати такий вигляд:

public void InCell(int x, int y, string n)// Додаємо в клітинку з координатами x,y текст n

 {

  sheet.Range[ConvertRange(x - 1, y)].Value = "'"+n;//sheet.Range - об"єкт який здійснює всі операції з клітинками

 }

Для зручності оголосимо ще одну функцію, яка буде повертати текст із клітинки екселю:

public string InCell(int x, int y)//Повертає текст, якій міститься у заданій клітинці

 {

  return sheet.Range[ConvertRange(x - 1, y)].Value; //працює аналогічно попередній функції

 }

Для покращення зовнішнього вигляду, читабельності документа, оголосимо процедуру, яка буде форматувати шрифт клітинки.

public void FormatFont(int x, int y, bool b = false, bool i = false, //змінює параметри шрифту в

bool u = false, int color = 0, int size = 0, string face = "") //заданій клітинці

 // х,у - координати клітинки

 // b, i, u - жирний, курсив, підкреслений шрифт

 // color - колір заданий у форматі 0хBBGGRR

 // size - розмір, face - назва шрифту

  {

   if (b) sheet.Range[ConvertRange(x-1, y)].Font.Bold = b; //якщо потрібно задаємо жирність

   if (i) sheet.Range[ConvertRange(x-1, y)].Font.Italic = i;//якщо потрібно задаємо курсив

   if (u) sheet.Range[ConvertRange(x-1, y)].Font.Underline = u;//якщо потрібно задаємо підкреслення

   if (color != 0) sheet.Range[ConvertRange(x-1, y)].Font.Color = color;//якщо потрібно задаємо колір

   if (size != 0) sheet.Range[ConvertRange(x-1, y)].Font.Size = size;//якщо потрібно задаємо розмір

   if (face != "") sheet.Range[ConvertRange(x-1, y)].Font.Name = face;//якщо потрібно задаємо новий шрифт

  }

Опишемо, також, можливість вставки формулу в клітинку екселю:

public void CellFormula(int x, int y, string f)// Додаємо формулу в потрібну клітинку

     // x, y - координати, f - формула

 {

  sheet.Range[ConvertRange(x-1, y)].Formula = f; //записуємо формулу

 }

Опишемо функцію зміни розміру клітинки. Зверніть увагу, в екселі одиниці виміру розмірів по горизонталі та одиниці виміру по горизонталі – різні, тобто розмір клітинки 20х20 не зробить її квадратною!

public void ResizeCell(int x, int y, int width, int height)//Масштабує потрібну клітинку книги

  // x, y, - координати, width, height - ширина та висота

 {

  if (height != 0) sheet.Range[ConvertRange(x-1, y)].RowHeight = height; //Якщо задана висота - змінюємо

  if (width != 0) sheet.Range[ConvertRange(x-1, y)].ColumnWidth = width; //Якщо задана ширина - змінюємо

 }

Створимо, для зручності, властивість зміни видимості екселю на екрані:

public bool visible //Властивість можна використовувати для регулювання видимості екселя на екрані

 {

  get { return excelapp.Visible; } // повертає статус видимості (видимий/невидимий)

  set { excelapp.Visible = visible; } // встановлює видимість екселю

 }

Для того, щоб розмістити логотип компанії на звіті, або ж, помістити кліше, нам може знадобитися процедура розміщення малюнку на листі:

public void InsertPicture(int left,int top,int width,int height,string name) //додає малюнок в книгу

   // left - позиція малюнку зліва,

   // top - позиція зверху,

   // width,height - ширинв та висота малюнку відповідно,

   // name - ім"я малюнку з абсолютним шляхом до нього

 {

sheet.Shapes.AddPicture(name,MsoTriState.msoFalse,MsoTriState.msoTrue,left,top,width,height).Select();

   // вставляє малюнок відповідно заданих параметрів, та виділяє його,

   // якщо потрібно в подальшому змінити

 }

І, на кінець, ми вже дійшли до самої основної процедури, процедури, яка безпосередньо і буде переносити дані в ексель:

     //Вставляє на лист екселю данні із потрібної сітки з даними

public void InsertTable(DataGridView dg,int left=1,int top=1,

  int hFSize=0,string hFname="",bool hB=false,bool hI=false,bool hU=false,int hColor=0,

  int bFSize=0,string bFName="",bool bB=false,bool bI=false,bool bU=false,int bColor=0)

     //dg - посилання на сітку з даними,

     //left,top - відступи від верхнього кута листа (по замовчуванню 1,1),

     //hFSize - розмір шрифта для рядка заголовків,

     //hFname - назва шрифта для рядка заголовків,

     //hB - жирність шрифта для рядка заголовків,

     //hI - курсив шрифта для рядка заголовків,

     //hU - підкреслення шрифта для рядка заголовків,

     //hColor - колір шрифта для рядка заголовків,

     //bFSize - розмір шрифта для рядків таблиці,

     //bFName - назва шрифта для рядків таблиці,

     //bB - жирність шрифта для рядків таблиці,

     //bI - курсив шрифта для рядків таблиці,

     //bU - підкреслення шрифта для рядків таблиці,

     //bColor - колір шрифта для рядків таблиц

   {

    int r = dg.RowCount; int c = dg.ColumnCount; //поміщаємо в змінні

     // r та с кількість рядків та стовпців відповідно

    for (int hc = 0; hc < c; hc++) //перебераємо всі стовпці по черзі через змінну hc

     {

      InCell(hc+left,top,dg.Columns[hc].Name+"");//дізнаємося заголовок стовпця з індексом hc,

     // та поміщаємо в відповідну клітинку ексель

      FormatFont(hc + left, top, hB, hI, hU, hColor, hFSize, hFname); //задаємо потрібне форматування клітинки

      }

       for (int cr = 0; cr < r; cr++) //перебираємо рядки сітки через змінну cr

          {

              for (int cc = 0; cc < c; cc++) //перебераємо стовпці сітки через змінну сс

                {

                 InCell(cc + left, cr + 1 + top, dg.Rows[cr].Cells[cc].Value + "");

                 //дізнаємося значення клітинки з індексом сс,cr та вставляємо в ексель

                 FormatFont(cc + left,cr+ 1+ top, bB, bI, bU, bColor, bFSize, bFName);//задаємо потрібне форматування клітинки

                }

            }

        }