Table Widget – wyższa szkoła jazdy

By: | Post date: Styczeń 1, 2018

TABLE widget jest już kawałkiem solidnego programu zaszytego w skromnym jednopinowym elemencie. Na upartego większość moich aplikacji dałaby się upakować w pojedynczą tablicę. Jest to oczywiście widget dwukierunkowy z możliwością przesyłania i odbioru danych wielowymiarowych. Naprawdę wielowymiarowych bo domyślny maksymalny rozmiar tablicy to 100 rzędów, które możemy jeszcze zwiększyć w ustawieniach serwera (ale tylko lokalnego). Jeśli widget BUTTON jest ONE MAN ORCHESTRA to tablica jest całkiem sporą orkiestrą symfoniczną. Więc zanosi się na dłuższą opowieść

Widget TABLE w wersji komercyjnej kosztuje 800 pkt. Sporo – choć wart jest ceny biorąc pod uwagę jego możliwości. Na szczęście na tym blogu zajmujemy się jedynie słuszną darmową wersją BLYNKa więc widgetów tablica możemy wstawić do swojej aplikacji ile dusza zapragnie.

Tablica jest w zasadzie dwuwymiarowa. Ale wyświetlane być mogą 3 pola tablicy <ikon>, <name> i <value>.

Konfiguracja widgeta.

Jest niewielka ale istotna. Na początek zdecydujemy ile, jakie i w jakiej kolejności pola chcemy wyświetlać. Do wyboru mamy

  • ikona
  • <name>
  • <value>

Muszą być minimum dwa zawsze i jednym z pól musi być NAME.

Pole ikony jest opcjonalne a ikona (zielona obrzydliwa kropka) jest jak na razie niezmienna.

Pole NAME musi być zawsze.

Pole VALUE jest opcjonalne. Jego wyświetlanie lub nie, nie ma wpływu na zapamiętywane w wirtualnym pinie dane. Te są zawsze dwuwymiarowe.

Do wyboru mamy jeszcze:

  • opcja zmiany miejsca wyświetlania rzędu. Zmiana miejsca nie zmienia faktycznej numeracji danego rzędu – ta pozostaje niezmienna niezależnie od kolejności wyświetlania
  • możliwość klikania w dany rząd (funkcja przycisk). Bardzo cenna właściwość pozwalająca w oparciu o tablicę budować złożone systemy sterowania – ale o tym później

Jak większość nietypowych, złożonych widgetów można go obsługiwać na dwa sposoby:  klasycznie i z predefinicją.

Widget TABLE – sterowanie (prawie) standardowe

Do zapisu danych do tablicy używamy nieco zmodyfikowanej procedury Blynk.virtualWrite() .

I tak dodanie pozycji (rzędu) tabeli realizujemy poprzez

Blynk.virtualWrite (Vpin, „add”, nr_rzedu, name, value);

np.

Blynk.virtualWrite (V10,  „add”,  2, „cokolwiek”, 77777);

Jeśli nie było wcześniej rzędu o numerze 2 nowy rząd z tym numerem zostanie umieszczony na końcu tabeli  nawet jeśli istnieją już rzędy o numerach wyższych! Taki mały siurpriz. Jeżeli mamy włączoną opcję zmiany kolejności rzędów możemy taki rząd przesunąć  sobie ręcznie na właściwe miejsce. Nie jest to duży problem bowiem tworzenie nowych rzędów tablicy z reguły wywoływane jest dla kolejnych numeracji – ale trzeba o tym pamiętać by nie zostać zaskoczonym układem tablicy.

Jeśli chcemy dodać rząd o numerze już istniejącym w tabeli nowa pozycja zastąpi poprzednią. a rząd trafi na koniec tabelicy

Danymi w tabeli mogą być dowolne typy zmiennych (jak to w BLYNKu) mimo iż nazwy pól (NAME, VALUE) sugerują coś innego.

Można więc bez problemu wpisać

Blynk.virtualWrite (V20, „add”, 0, 12345.345, true);

i na ekranie zobaczymy coś takiego (patrz na rząd 3 mimo, iż ma numer 0!)

W rzędzie drugim widoczna jest maksymalna liczba znaków jakie można wyświetlić w poszczególnych polach. Dla pola NAME jest to 25 znaków dla pola VALUE – 11. Jeśli w konfiguracji widgetu zrezygnujemy z pola VALUE maksymalna liczba znaków pola NAME wzrasta do 35.

Dane przesyłane do tego widgetu zapamiętywane są na serwerze. To co widzimy na ekranie jest tylko ich graficzną obróbką.  Dane możemy bez problemu zapisać na serwer  ale nie możemy ich z serwera odczytać. Można je tylko wyświetlić w widgecie.  Oznacza to iż w programie musimy stworzyć i przechowywać równoległą tablicą danych  by móc na niej swobodnie operować. Jeśli chcemy odtworzyć zawartość widgetu tablet po resecie mikrokontrolera naszą równoległą tablicę trzeba zapisać w pamięci nieulotnej.

Widget ma swoją oddzielną procedurę do aktualizacji zawartości konkretnego rzędu tablicy

Blynk.virtualWrite (V1, „update”, nr_rzedu, „UpdatedName”, „UpdatedValue”);

Działa podobnie jak dodanie rzędu z istniejącym już numerem tz. podmienia wartości pól na nowe ale  nie zmienia kolejności rzędów w tabeli.

Możemy wykasować całą zawartość tablicy (wszystkie dane na serwerze) poleceniem

Blynk.virtualWrite (V1, „clr”);

Nie możemy natomiast wykasować wybranego rzędu. A szkoda. Musimy to zrobić w równoleglej tablicy programie i ponownie zapisać ją do pinu wirtualnego.

Widget TABLE jest całkowicie ślepy na kolory. To jeden z niewielu elementów w którym możemy wybrać dowolny kolor o ile jest to kolor obrzydliwie zielony. Tym kolorem możemy z poziomu programu podświetlić sobie wybrany rząd poleceniem:

Blynk.virtualWrite (V1, „pick”, nr_rzedu);

Efekt nie jest urzekający ale czytelny.

Jak wspomniałem nie ma możliwości odczytu zawartości danych z tablicy. Standardowa procedura odczytu danych jednak działa zwracając aż 3 różne informacje

BLYNK_WRITE(V20) {
  String akcja = (param[0].asStr());
  Blynk.virtualWrite(V21, k);
  String nr_rzedu = (param[1].asStr());
  Blynk.virtualWrite(V22, j);
    String nr_rzedu = (param[2].asStr());
  Blynk.virtualWrite(V23, i);
  
}

Wartości zostaną odczytane tą procedurą jeśli po pierwsze ustawiliśmy opcje w konfiguracji widgeta by „naciskać” wybrane rzędy tablicy i przenosić je w inne miejsce tablicy, po drugie gdy wykonamy w aplikacji którąś z tych czynności.

Przy naciśnięciu lub zwolnieniu rzędu tablicy w pierwszej zmiennej param[0].asStr() pojawi się string z napisem <select> <deselect> zaś w drugiej zmiennej param[1].asInt() nr ostatnio naciśniętego/ zwolnionego rzędu. Wartość trzeciej zmiennej nie ma w tym przypadku znaczenia. Ciekawostką jest iż wszystkie nowo tworzone rzędy tablicy ustawione są domyślnie jako <select>.

Możemy też ręcznie zmienić kolejność poszczególnych rzędów. Przeniesienie pierwszego rzędu na koniec tablicy generuje wartość <order> na pierwszej pozycji a na kolejnych  numery rzędów początkowego i końcowego operacji przeniesienia.

Oczywiście działanie typu select/deselect i order możemy też wywołać procedurami z naszego programu. I tak np.

Blynk.virtualWrite (V20, „deselect”, 3);

da identyczny efekt do opisanego wyżej ręcznego naciśnięcia rzędu tablicy w aplikacji. Zaś

Blynk.virtualWrite (V20, „order”, 1, 5);

przeniesie rząd 1 na pozycję 5 (rzędy w tablicy numerowane są od „0”).

 

Widget TABLE – wywołanie z predefinicją

Dla tego widgetu stworzono drugi równoległy sposób wywoływania procedur w programie czemuś to nazwany „zaawansowanym”. Na początku musimy zdefiniować obiekt table (lub o innej dowolnej nazwie) i połączyć go z jakimś wirtualnym pinem

WidgetTable table;
BLYNK_ATTACH_WIDGET (table, V1);

Teraz do dyspozycji mamy następujące procedury których działanie jest identyczne do wyżej opisanych:

table.addRow(nr_rzedu, NAME, VALUE); – dodanie rzędu

table.updateRow(nr_rzedu, NAME, VALUE); – modyfikacja zawartości rzędu

table.pickRow(nr_rzedu); – podświetlenie rzędu

table.clear(); – wykasowanie danych tablicy

table.onOrderChange([](int indexFrom, int indexTo) { });  funkcja odczytująca zmianę pozycji rzędów

table.onSelectChange([](int index, bool selected) {} funkcja odczytująca naciśnięty/zwolniony rząd

W programie możemy więc obsługiwać widget na dwa sposoby. Który lepszy – to już decyzja na wskroś indywidualna. Sam widget wart jest jednak tego by znalazł miejsce w każdym większym projekcie.

28

Dodaj komentarz

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

Translate »