Informatyka 
 
Piszemy własną bibliotekę do Arduino – sterownik Nixie
Narcyz
Gdy przygotujemy jakiś układ elektroniczny współpracujący z Arduino, warto przygotować dla niego program w takiej postaci, do jakiej przyzwyczajeni są użytkownicy tej platformy – w postaci biblioteki, zawierającej przykłady.

Budując nowe urządzenie które jest sterowane systemem mikroprocesorowym lub komputerem, warto przygotować program który je obsługuje w takiej formie, by mógł być używane przez innych konstruktorów. W przypadku gdy nasz program piszemy w środowisku Arduino, warto przygotować odpowiednia bibliotekę. Jest to naprawdę bardzo proste bo cała bibliotek składa się wyłącznie z plików tekstowych.

Biblioteki przechowywane są w określonej lokalizacji. Domyślnym miejscem w systemie MS Windows jest katalog /Program files/Arduino/libraries na dysku na którym zainstalowany jest system. Każda biblioteka jest umieszczona w oddzielnym podfolderze który zawiera dwa katalogi:

  • src – zawierający wszystkie pliki źródłowe biblioteki – czyli te pliki które będą kompilowane
  • examples – przykładowe użycia tej biblioteki – przydatne by zobaczyć jak powinno się jej używać. Przydatne także jeśli użytkownik nie m pomysłu na specjalnie zaawansowane programowania i wystarczy nam to co przewidzieliśmy albo to co sami zaprogramowaliśmy.
Ponadto w głównym folderze należy umieścić kilka specjalnych plików które omówimy na końcu.

Dystrybucja takiej biblioteki jest bardzo prosta – wystarczy spakować całość w pojedynczy plik .zip, by środowisko Arduino umiało go zainstalować.

src – pliki źródłowe

Pliki źródłowe powinny mieć taką samą nazwę jak nazwa biblioteki, która jest przy okazji także nazwą jej katalogu. Potrzebujemy dwóch plików: pliku nagłówkowego – z rozszerzeniem .h – zawierającego deklarację wszystkich zmiennych stałych oraz klas czy obiektów globalnych które składają się na naszą bibliotekę, oraz pliku .cpp zawierającego definicję wszystkich funkcji i metod.

W przypadku naszego drivera do lamp Nixie, zadeklarujemy klasę obsługującą wyświetlacz, w której będziemy mieli tylko dwie metody:

  • konstruktor pozwalający na przekazanie i zapamiętanie do których pinów Arduino wyświetlacz jest podłączony, oraz
  • funkcję przesyłającą pojedynczą cyfrę do wyświetlacza.

/*

Nixie tube display driver - serially sends four bits to given pins

*/

#ifndef NIXIE_h
#define NIXIE_h

#include "Arduino.h"

class Nixie  {
    public:
        Nixie(byte dataPin, byte clockPin);
		
        void print(byte valueOrDigit);
		
    private:
        byte dataPin_;
        byte clockPin_;
		
        static const int delayTime_ = 2;
};

#endif

W klasie zadeklarowaliśmy także dwie zmienne w których pamiętane będą numery wyjść płytki, oraz jedną stałą, w której będziemy pamiętać czas jaki będzie podstawą czasu sygnału szeregowego przesyłanego do płytki. Na razie nie przewidujemy jego zmiany, ale może w przyszłości, w kolejnej wersji biblioteko to się zmieni.

Zauważmy też dodany na początku pliku komentarz. Nie jest on obowiązkowy, ale to na prawdę dobry zwyczaj by opisywać pliki określając do czego one służą, oraz kto i kiedy je stworzył.

Plik z rozszerzeniem .cpp zawiera implementacje metod zadeklarowanych w pliku nagłówkowym. Ponieważ do jego poprawnej kompilacji potrzebna jest wiedza zawarta w pliku nagłówkowym – włączamy go dyrektywą #include która włącza zawartość wskazanego pliku w miejscy w którym została zapisana.

Kod obu funkcji jest bardzo prosty, a jego analizę pozostawiamy czytelnikowi jako ćwiczenie.

/*

Nixie driver - serially sends four bits to given pins

*/

#include "Nixie.h"

Nixie::Nixie(byte dataPin, byte clockPin)
:   dataPin_(dataPin)
,    clockPin_(clockPin)
{	
    pinMode(dataPin_, OUTPUT);
    pinMode(clockPin_, OUTPUT);
}

void Nixie::print(byte valueOrDigit)  {
    digitalWrite(dataPin_, 0);
    digitalWrite(clockPin_, 0);
    delay(delayTime_);
    for (byte i=0; i<4; ++i) {
        digitalWrite(dataPin_, (valueOrDigit & 8) ? 1 : 0);
        valueOrDigit <<= 1;
        delay(delayTime_);
        digitalWrite(clockPin_, 1);
        delay(delayTime_);
        digitalWrite(clockPin_, 0);
        delay(delayTime_);
    }
    digitalWrite(dataPin_, 0);
} 

Umieszczenie tylko tych dwóch plików w odpowiednim podkatalogu biblioteki …/Arduino/libraries powoduje, że co prawda możemy z tej biblioteki korzystać, ale nie jest ona rozpoznawana przez środowisko programistyczne Arduino. Aby naprawić ten błąd – potrzebujemy specjalnego pliku zawierającego definicję biblioteki jako całości. W pliku tym umieszczamy wszystkie niezbędne informacje o bibliotece:

library.properties
name=Nixie
version=1.0.0
author=Narcyz
maintainer=WGan <wgan@wgan.pl>
sentence=Allows communication with serial nixie driver described by WGan at http://nowyolimp.net/preview.php?iss=-&id=1086
paragraph=This library allows an Arduino board to control Nixie.
category=Display
url=http://nowyolimp.net/preview.php?iss=-&id=1085
architectures=*

README.adoc
Kolejnym plikiem jaki powinniśmy umieścić w głównym katalogu naszej biblioteki – to plik z informacjami dla użytkownika biblioteki. Umieszczamy tu informacje o autorstwie, oraz warunkach licencji. Może on wyglądać na przykład tak:

= Nixie Library for Arduino =

This library allows an Arduino board to control Nixie displays

== License ==

Copyright (C) 2016 Nowyolimp.net
Copyright (c) 2010 Arduino LLC. All right reserved.

This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.

This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.

You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 

keywords.txt
Ostatni z przydatnych plików – to informacja to tym jak należy kolorować specjalne słowa jakie używamy w naszej bibliotece – na przykład nazwa klasy albo metod.

#######################################
# Syntax Coloring Map For Nixie
#######################################

#######################################
# Datatypes (KEYWORD1)
#######################################

Nixie	KEYWORD1	Nixie

#######################################
# Methods and Functions (KEYWORD2)
#######################################

print	KEYWORD2

#######################################
# Constants (LITERAL1)
#######################################

examples
Nasza biblioteka nie byłaby gotowa jeśli nie dodalibyśmy od siebie przykładów jej użycia. Najprościej przygotować je po prostu pisząc odpowiednie programy a potem kopiując je do podkatalogu exaples. Mogą to być dokładnie te same projekty, na których testowaliśmy nasza bibliotekę podczas jej pisania. Może to być na przykład wyświetlanie kolejnych cyfr na wyświetlaczu.

#include "Nixie.h"

/*
 * Nixie connected to:
 *  - data - pin 11
 *  - clock - pin 9
 */

Nixie nixie(11, 9); 

void setup() {
    // put your setup code here, to run once:
    nixie.print(0);
    nixie.print(0);
    nixie.print(0);
    nixie.print(0);
}

byte x = 0;

void loop() {
    // put your main code here, to run repeatedly:
    nixie.print(x);
    delay(1000);
    ++x;
    if (x==10) x = 0;
} 

Lub zrealizowanie zegara który odlicza do zera:

#include "Nixie.h"

/*
 * Nixie connected to:
 *  - data - pin 11
 *  - clock - pin 9
 */

Nixie nixie(11, 9); 

void setup() {
    // put your setup code here, to run once:
    nixie.print(0);
    nixie.print(0);
    nixie.print(0);
    nixie.print(0);
}

byte x = 0;

void loop() {
    // put your main code here, to run repeatedly:
    static byte mins = 15;
    static byte secs = 59;

    nixie.strobe(true);
    byte m1 = mins/10;
    byte m2 = mins%10;
    nixie.print(m2);
    nixie.print(m1);
    
    byte s1 = secs/10;
    byte s2 = secs%10;
    nixie.print(s2);
    nixie.print(s1);
    
    nixie.strobe(false);
    
    if (!secs)  {
        secs = 59;
       
        if (!mins)  {
            mins=99;
        }
        else  {
            --mins;
        }
    } 
    else  {
        --secs;
    }

    delay(1000);
} 

Możemy też oba programy dodać do biblioteki jako przykłady.

 
Opinie
 
Facebook
 
  
39224 wyświetlenia

numer 11/2016
2016-11-01

Od redakcji
Aktualności
Dla młodszych
Filozofia
Fizyka
Historia
Kącik poezji
Literatura
Rozmaitości

nowyOlimp.net na Twitterze

nowy Olimp - internetowe czasopismo naukowe dla młodzieży.
Kolegium redakcyjne: gaja@nowyolimp.net; hefajstos@nowyolimp.net