Wykresy ZedGrapf

W niniejszej części zajmiemy się tematem wizualizacji danych. Wiadomo, że niemal każdy szanujący się program musi wyświetlać wyniki swojej pracy w czytelnej i estetycznej formie umożliwiającej przeglądanie wyników pracy przez osoby używające tego programu. Od funkcjonalności i czytelności wyników może zależeć sukces lub porażka naszej pracy. Dlatego też warto położyć nacisk na estetyczną i czytelną reprezentację danych. Wizualizacja, jaką będziemy się zajmować w niniejszej części to wykresy, raporty oraz drukowanie.

Tworzymy Wykresy (komponent ZedGraph)

Załóżmy, że piszesz program dla szkoły ilustrujący wykres funkcji cosinus. Jak jednak zilustrować proces tworzenia cosinusoidy? Nie musisz prezentować samej funkcji tworzącej wykres. Jako programista masz za zadanie zaprezentować wizualizację efektu końcowego. Innym przykładem jest przedstawienie szefowi wyników sprzedaży za poszczególne miesiące. Oczywiście możesz to zrobić drukując po prostu wybrane rekordy z bazy danych i przedstawić szefowi kartkę zapisaną liczbami. Jednak twój szef będzie bardziej zadowolony, jeśli przedstawisz mu wykres słupkowy zawierający wartość sprzedaży z całego roku. A dodatkowo wstawisz linię trendu obrazującą wzrost lub spadek sprzedaży. Są to tylko przykłady zastosowania wykresów. Przekonasz się, że podczas pracy spotkasz się z wieloma sytuacjami, które wymuszą na tobie tworzenie wykresów. Warto więc przyjrzeć się możliwością pakietu ZedGraph, który umożliwi ci tworzenie wspaniałych kolorowych wykresów pobudzających wyobraźnię nawet najbardziej wymagających szefów.

Komponent jest dostępny na stronie http://zedgraph.sourceforge.net/samples.html. Warto zaopatrzyć się w najnowszą jego wersję, która z pewnością oferuje nowe możliwości. Po zapisaniu komponentu na dysk należy go zdekompresować. Powstanie wówczas plik o rozszerzeniu DLL, który jest już właściwym komponentem. Dodatkowo pakiet zawiera lokalizację wielu języków. Niestety nie ma tam języka polskiego, ale jak się przekonamy, nie jest to wielką tragedią, gdyż nasz wykres opiszemy sami w rodzimym języku. Folder z komponentem przenieś do dowolnego folderu. Pamiętaj, że każdy utworzony przez ciebie program będzie go wymagał. Będzie więc dostarczany wraz z programem dla użytkownika końcowego.

Aby zainstalować nowy komponent, wyświetl okno komponentów używając opcji w menu Tools->Choose Tolbox Item.

zedgraph1

Wyświetlona lista zawiera komponenty dostępne dla Visual Studio. Następnie używając przycisku Browse… Następnie wskaż plik ZedGraph.dll w katalogu, do którego zapisałeś komponent i naciśnij przycisk Open. Jak widać, na końcu listy dostępnych komponentów pojawił się komponent ZedGraphControl. Zaznacz go, jeśli nie jest zaznaczony i użyj przycisku OK, aby zamknąć okno dialogowe.

zedgraph2

Nowy komponent pojawi się na pasku komponentów (ToolBox) jako ikona o nazwie ZedGraphControl. Po tych czynnościach możesz już używać komponentu w swoich projektach.

Wykres liniowy

Spróbujmy teraz napisać program korzystający z nowego komponentu. Utwórz nowy projekt z menu FileàNew Project… lub użyj kombinacji Ctrl+Shift+N. Wybierz Windows Application i wpisz nazwę projektu – WykresCosinus.

  • Na nowej formie umieść komponent ZedGraphControl,
  • Zmień jego właściwość Dock na Fill,
  • Zmień rozmiar okna na odpowiedni dla twojego ekranu i upodobania.

zedgraph3

Jeśli twój projekt wygląda jak ten z obrazka powyżej, to oznacza, że jesteś na dobrej drodze. Jak widać przy umieszczeniu komponentu na formatce przyjmuje on zdefiniowane wartości domyślne. Nie jest to jednak problem, gdyż za chwilę sami zaprogramujemy nasz własny wykres.

Przejdź do trybu edycji kodu źródłowego i wstaw na początku odwołanie do biblioteki ZedGraph

using ZedGraph;

A następnie w miejscu po InitializeComponent, tworzymy nasz wykres.

public partial class Form1 : Form
  {
   public Form1()
  {
   InitializeComponent();
 
   GraphPane myPane = zedGraphControl1.GraphPane;
   myPane.Title.Text = "Demonstracja fukncji cosinus";
   myPane.XAxis.Title.Text = "Opis osi poziomej X";
   myPane.YAxis.Title.Text = "Wartość zmiennej sinus";
   myPane.Legend.Position = ZedGraph.LegendPos.Bottom; 
   myPane.Chart.Fill = new Fill(Color.White, Color.FromArgb(255, 255, 210), -45F); 
 
   PointPairList list = new PointPairList();
     double x, y, y2;
       for (int i = 0; i < 80; i++)
        {
         x = (double)i * 5.0;
         y = Math.Cos((double)i * Math.PI / 15.0) * 16.0;
           y2 = y * 13.5;
           list.Add(x, y);
         }
 
   // Wykres liniowy
 LineItem myCurve = myPane.AddCurve("Wykres cosinus", list, Color.Blue, 
                                                      SymbolType.TriangleDown);
  myCurve.Line.Width = 1; // Grubość linii wykresu
  myCurve.Symbol.Fill = new Fill(Color.Brown); 
 
  zedGraphControl1.AxisChange();
  zedGraphControl1.Refresh();
        }

Uruchom program klawiszem F5. Jeśli wszystko dobrze wpisałeś, program powinien wyglądać tak:

zedgraph4

Widać więc, jak prostym sposobem utworzyliśmy wykres funkcji. Teraz spróbujemy przeanalizować nasz program krok po kroku, aby dowiedzieć się więcej o tworzeniu wykresu.

GraphPane myPane = zedGraphControl1.GraphPane;

W tej linii tworzymy nowy panel, na którym umieszczamy osie wykresu. Na panelu możemy umieszczać wykresy liniowe, kołowe i inne. W tym przypadku jest to wykres liniowy.

 myPane.Title.Text = "Demonstracja fukncji cosinus";

Tutaj deklarujemy tytuł wykresu. Możliwości wykorzystania pozostawiam twojej wyobraźni.

myPane.XAxis.Title.Text = "Opis osi poziomej X";

Opis osi poziomej X. Tutaj możesz wpisać opis osi, która może przedstawiać np. czas

myPane.YAxis.Title.Text = "Wartość zmiennej sinus";

Podobnie, lecz dotyczy osi pionowej Y, oznaczającej zwykle zmieniającą się wartość  obserowanego zjawiska.

myPane.Legend.Position = ZedGraph.LegendPos.Bottom;

Opcja umożliwia umieszczanie legendy wykresu. Legenda zwykle opisuje osie wykorzystywane na wykresie.

myPane.Chart.Fill = new Fill(Color.White,Color.FromArgb(255,255,210),-45F);

Wypełnienie obszaru kolorem. W naszym przypadku jest to kolorowy gradient. Warto poeksperymentować w celu dobrania kolorów obszaru wykresu, gdyż wygląda to bardzo efektownie.

PointPairList list = new PointPairList();
     double x, y, y2;
       for (int i = 0; i < 80; i++)
        {
         x = (double)i * 5.0;
         y = Math.Cos((double)i * Math.PI / 15.0) * 16.0;
           y2 = y * 13.5;
           list.Add(x, y);
         }

Tworzenie tablicy zawierającej wartości X i Y niezbędnej do wykresu. W naszym przypadku wykorzystaliśmy przebieg funkcji cosinus, ale oczywiście mogą to być dowolne parametry.

Jeśli chcesz utworzyć wykres liniowy przedstawiający własne parametry, zamiast generowania wartości przebiegu funkcji cosinus, użyj list.add(X,y), aby je wprowadzić.

list.Add(3, 45);
list.Add(5, 25);
list.Add(7, 65);

Możesz wprowadzić dowolną ilość wartości. Wykres sam dostosuje swoją skalę do wartości maksymalnych oraz minimalnych wykresu.

LineItem myCurve = myPane.AddCurve("Wykres cosinus", list, Color.Blue, SymbolType.TriangleDown);

Teraz dodajemy do obszaru wykresu element stanowiący wykres. Jest to linia. Jak widać, linia wykresu przyjmuje kilka parametrów: Nazwę linii wykresu, zmienną tablicową, kolor linii oraz typ punktów wykresu wartości mierzonych.

myCurve.Line.Width = 1; // Grubość linii wykresu

Dopełnieniem całości jest opcjonalne ustalenie grubości linii.

myCurve.Symbol.Fill = new Fill(Color.Brown);

Oraz wypełnienia punktów wartości mierzonych.

zedGraphControl1.AxisChange();
zedGraphControl1.Refresh();

Dwie powyższe linijki zatwierdzają zmianę osi oraz powodują odświeżenie obszaru wykresu. Ostatnia linia nie jest konieczna ale przydaje się czasem, gdy konieczne staje się odświeżenie wykresu.

Wykres słupkowy

Teraz zajmiemy się tworzeniem wykresu słupkowego. Utwórz nowy projekt. Wybierz Windows Application i wpisz nazwę projektu – WykresSlupkowy.

•   Na nowej formie umieść komponent ZedGraphControl,
•   Zmień jego właściwość Dock na Fill aby dostosować wykres do wielkości okna.

Ponownie wpisujemy kod tworzący wykres słupkowy wartości zysku (oczywiście bardzo optymistyczny 🙂 )

GraphPane myPane = zedGraphControl1.GraphPane;
 myPane.Title.Text = "Zysk w roku 2005";
 myPane.XAxis.Title.Text = "Miesiące roku 2005";
 myPane.YAxis.Title.Text = "Zysk w mln zł.";
 myPane.Legend.Position = ZedGraph.LegendPos.Bottom;
 myPane.Chart.Fill = new Fill(Color.White, Color.FromArgb(225, 255, 110), -45F);     
 
string[] labels = { "Sty", "Lut", "Mar", "Kwi", "Maj", "Czer", "Lip", "Sie", "Wrz", 
                                                          "Paź", "Lis", "Gru" };
 
double[] yr = { -1000, -500, 500, 1000, 2300, 2700, 3000, 2800, 2600, 2800, 3000, 
3500 };
 
BarItem myBar = myPane.AddBar("Zysk w poszczególnych miesiącach", null, yr, Color.Red);
  myPane.XAxis.Scale.TextLabels = labels; // Punkty wykresu są etykietami
  myPane.XAxis.Type = AxisType.Text;
  myPane.YAxis.Title.Text = "Wartość w mln zł.";
 
 
 LineItem myCurve = myPane.AddCurve(null, null, yr, Color.Black, SymbolType.Circle);
 myCurve.Line.Fill = new Fill(Color.White, Color.Aqua, -45F);
 
 zedGraphControl1.AxisChange();
 BarItem.CreateBarLabels(myPane, false, "f0");

Jak zapewne zauważyłeś, powyższy kod jest bardzo podobny do poprzedniego. Dokładniejszej analizy wymaga jednak kilka linijek.

string[] labels = { "Sty", "Lut", "Mar", "Kwi", "Maj", "Czer", "Lip", "Sie", "Wrz", "Paź", "Lis", "Gru" };
double[] yr = { -1000, -500, 500, 1000, 2300, 2700, 3000, 2800, 2600, 2800, 3000, 3500 };

Powyższe linie kodu odpowiadają za utworzenie danych do wykresu. Tablica label tworzy etykiety dla osi x. Natomiast tablica yr z liczbami zmiennoprzecinkowymi tworzy oś wartości y.

myPane.XAxis.Scale.Max = 13;
myPane.YAxis.Scale.Max = 4500;

Właściwość Max oraz Min można wykorzystać do zdefiniowania wartości minimalnych oraz maksymalnych obszaru wykresu. Zwykle komponent sam dobiera wielkość skali. Czasem jednak będziemy chcieli zawęźić lub powiększyć zakres wykresu.

BarItem.CreateBarLabels(myPane, false, "f0");

Linia ta tworzy etykiety wartości danych wg podanego formatu liczbowego. Jest to opcja bardzo przydatna, gdyż umożliwia łatwe odczytanie wartości konkretnego słupka czyniąc wykres bardziej czytelnym.

Wykres kołowy

Wykresy kołowe stosować można do procentowago udziału poszczególnych danych w całości. Całość, czyli 100% w tym wypadku oznacza całe koło. Wycinki koła zostają przeliczone na procentowe porcje, oznaczają większy lub mniejszy udział w całości. Napiszmy więc przykład wykresu kołowego. Na wykresie przedstawimy wymyślone dane udziału w rynku poszczególnych firm informatycznych. Analizować będziemy rynek, w którym działa 4 liczące się firmy.

•    AX Computer – 1.230
•    System – 2.800
•    Bajt – 2.340
•    Bit Komputer – 15.000

Reszta mniej istotnych graczy na rynku, będzie zaznaczona jako inni a wartość ich udziału  wynosi 1.000.

Jak zawsze rozpoczynając nowy przykłąd tworzymy nowy projekt. Nadajemy mu nazwę, np. WykresKolowy i umieszczamy na nim komponent ZedGraphControl. Zmień jego właściwość Dock ustawiamy na Fill i przejdź do edycji kodu źródłowego.

GraphPane myPane = zedGraphControl1.GraphPane;
 
 myPane.Title.Text = "Udział firm informatycznych w rynku";
 myPane.Title.FontSpec.IsItalic = true;
 myPane.Title.FontSpec.Size = 24f;
 myPane.Title.FontSpec.Family = "Times New Roman CE";
 
 myPane.Fill = new Fill(Color.White, Color.DarkMagenta, 45.0f);
 myPane.Chart.Fill.Type = FillType.None;
 
 myPane.Legend.Position = LegendPos.Float;
 myPane.Legend.Location = new Location(0.95f, 0.15f, 
 
CoordType.PaneFraction,AlignH.Right, AlignV.Top);
 myPane.Legend.FontSpec.Size = 10f;
 myPane.Legend.IsHStack = false;
 
PieItem firma1 = myPane.AddPieSlice(1230, Color.Navy, Color.White, 45f, 0, "AX Komputer");
PieItem firma2 = myPane.AddPieSlice(2800, Color.SandyBrown, Color.White, 45f, 0.2, "System");
PieItem firma3 = myPane.AddPieSlice(2340, Color.Chartreuse, Color.White, 45f, .0, "Bajt");
PieItem firma4 = myPane.AddPieSlice(15000, Color.LimeGreen, Color.White, 45f, 0, "Bit Komputer");
PieItem firma5 = myPane.AddPieSlice(1000, Color.Red, Color.Yellow, 45f, 0, "Inni");
 
 firma5.LabelDetail.FontSpec.FontColor = Color.Blue;
 
// Podsumowanie wartości do wykresu                                                               
 CurveList listawart = myPane.CurveList;
   double total = 0;
   for (int x = 0; x < listawart.Count; x++)
     total += ((PieItem) listawart[x]).Value;
 
TextObj opiswykr = new TextObj("Wartość udziału \n w rynku w \n roku 2005", 0.18F, 0.40F, CoordType.PaneFraction);
 myPane.GraphObjList.Add(opiswykr);
 
 zedGraphControl1.AxisChange();

Skompiluj i uruchom teraz program za pomocą klawisza F5. Wyniki twojej pracy powinny wyglądać następująco. Jak widzisz, wykres jest czytelny.

wykrersy223

Tak jak poprzednio, dokonamy teraz analizy kilku nowych parametrów wykresu.

myPane.Title.Text = "Udział firm informatycznych w rynku";
 myPane.Title.FontSpec.IsItalic = true;
 myPane.Title.FontSpec.Size = 24f;
 myPane.Title.FontSpec.Family = "Times New Roman CE";

W powyższych liniach ustalamy tytuł wykresu i modyfikujemy czcionkę dla uzyskania lepszego efektu.

myPane.Chart.Fill.Type = FillType.None;

Powyższa linia może wydawać się nieco mylna. Dzięki wypełnieniu FillType.None, nie wypełniamy obszaru wykresu. Dzięki temu tło panelu będzie ładnie wypełnione. Spróbuj pominąć tę linię, aby dokłądnie zobaczyć jej pozytywne działanie.

myPane.Legend.Position = LegendPos.Float;
myPane.Legend.Location = new Location(0.95f, 0.15f, AlignH.Right, AlignV.Top);

Ustalamy umiejscowienie legendy oraz wyrównanie w poziomie oraz pionie.

 myPane.Legend.FontSpec.Size = 10f;
 myPane.Legend.IsHStack = false;

Ustalamy rozmiar czcionki oraz informujemy, że legenda będzie wyświetlana jako lista pionowa.

PieItem firma1 = myPane.AddPieSlice(1230, Color.Navy, Color.White, 45f, 0, "AX Komputer");

Dodajemy wycinek koła wraz z wartością (1230), definiujemy kolory, ustalamy kąt, ustalamy odcięcie wycinka od koła wykresu oraz nadajemy etykietę.

 firma5.LabelDetail.FontSpec.FontColor = Color.Blue;

Dla każdego z wycinka można ustalić dowolny kolor. Powyżej zdefiniowaliśmy, że firma5 będzie wyświetlana czcionką niebieską.

CurveList listawart = myPane.CurveList;
   double total = 0;
   for (int x = 0; x < listawart.Count; x++)
     total += ((PieItem) listawart[x]).Value;

Na koniec należy dodać wszystkie elementy wykresu na panel. Powyższa pętla robi to automatycznie.

TextObj opiswykr = new TextObj("Wartość udziału \n w rynku w \n roku 2005", 0.18F, 0.40F, CoordType.PaneFraction);
 myPane.GraphObjList.Add(opiswykr);

Ciekawym elementem jest także etykieta dodawana obok wykresu, stanowiąca informację o samym wykresie.

Na tym zakończyliśmy wstęp do tworzenia wykresów za pomocą komponentu  ZedGraphControl. Potrafisz już tworzyć wykresy słupkowe, liniowe oraz kołowe. Spróbuj poeksperymentować zmieniając parametry i wartości danych. W opracowaniu pominęliśmy  przydatną możliwość powiększania obszaru wykresu czy tworzenia innych, bardziej rozbudowanych i fantazyjnych wykresów. Opis ten stanowi jedynie wstęp do ogromnej funkcjonalności tej biblioteki a jej opisanie zajęłoby większość niniejszego opracowania. Więcej informacji o możliwościach jej wykorzystania  znajdziesz na stronie domowej projektu oraz innych stronach traktujących o tym narzędziu.

457total visits,1visits today

Tagi , .Dodaj do zakładek Link.

Dodaj komentarz

Twój adres email nie zostanie opublikowany. Pola, których wypełnienie jest wymagane, są oznaczone symbolem *

+ 13 = 16