Po module z układem Si5351 i bibliotece do jego sterowania przyszedł czas, żeby to jakoś wykorzystać w praktyce. Za namową i przy gorącym dopingu Piotra SP9EGM powstał sterownik syntezera przeznaczony dla odbiorników SDR. Projekt oparty jest o Arduino i właściwie składa się z kodu programu oraz schematu połączeń. Kwestię sposobu fizycznego wykonania układu i ewentualnego projektu płytki drukowanej pozostawiam do rozstrzygnięcia czytelnikom. U mnie układ powstał po prostu na płytce stykowej.
Funkcjonalność
Podstawową funkcją sterownika jest generowanie sygnału taktującego dla detektora kwadraturowego jaki zastosowany jest w większości popularnych odbiorników SDR. Zwykle wymagane jest, by częstotliwość sygnału sterującego była czterokrotnie wyższa niż częstotliwość sygnału odbieranego, a układ Si5351 jest w stanie zapewnić taki sygnał dla całego zakresu KF.
Interakcja ze sterownikiem odbywa się za pomocą taniego enkodera mechanicznego z przyciskiem oraz dwóch klawiszy. Nic nie stoi jednak na przeszkodzie, aby wykorzystać lepszej jakości enkoder optyczny lub magnetyczny – próby pokazały, że współpracują one z układem bez konieczności wprowadzania zmian. Parametry sterownika prezentowane są na standardowym wyświetlaczu LCD 16×2 znaków.
Dodatkowo sterownik umożliwia sterowanie filtrami pasmowymi w zależności od ustawionej częstotliwości. Sterowanie odbywa się za pomocą układu dekodera BCD 4028, co w połączeniu z elastycznym sposobem konfiguracji w kodzie programu sprawia, że sterownik może współpracować z wieloma dostępnymi modułami filtrów (np. konstrukcji Waldka SP2JJH czy tymi od TRX Omega).
W celu ułatwienia pracy sterownik wyposażono w możliwość zapamiętywania częstotliwości i ich szybkiego przywoływania.
Konstrukcja
Proponowany schemat połączeń przedstawiony jest na rysunku. Jest to jedynie propozycja, ponieważ kod programu jest elastyczny i umożliwia indywidualną konfigurację wedle preferencji użytkownika. Aby ułatwić dostosowanie programu wszystkie opcje konfiguracyjne umieszczone są w osobnym pliku – config.h. Etykiety połączeń na schemacie są zgodne z nazewnictwem zastosowanym w tym pliku, co powinno rozwiać wszelkie wątpliwości gdyby nazwy okazały się niejednoznaczne.
Jedynymi połączeniami, które absolutnie muszą pozostać tak, jak na załączonym schemacie jest interfejs I2C dla modułu Si5351. Połączenia impulsatora (ENCODER_A i ENCODER_B) również podlegają pewnym ograniczeniom. Otóż ich proste przenoszenie związane tylko ze zmianą numerów pinów w pliku config.h możliwe jest jedynie w zakresie wyprowadzeń D2 – D7. Bardziej zaawansowani użytkownicy mogą przenieść połączenia enkodera również na inne piny Arduino, ale będzie to wymagało zmiany wektora przerwania PCI, do którego podpięta jest procedura obsługi „kręciołka”.
Program
Program sterownika dostępny jest w postaci skeczu Arduino. Jak już wcześniej wspomniałem wszystkie parametry, które użytkownik może chcieć zmienić starałem się wydzielić do pliku config.h. Do poprawnej kompilacji potrzebna jest oczywiście biblioteka do obsługi Si5351. Dodatkowo wymagana jest jeszcze biblioteka Rotary do obsługi enkodera. Niestety nie znam jej pochodzenia, ale można ją pobrać poniżej wraz z właściwym kodem programu.
Konfiguracja pasm i filtrów
Na samym końcu pliku config.h znajduje się sekcja ustawień pasm i sterowania filtrów. Opiszę ją w tym miejscu bardziej szczegółowo, by wprowadzanie w niej zmian nie było trudne.
/*********************************/ /* Bands & Filters */ /*********************************/ #define BAND_NUM 9 PROGMEM const uint32_t lower_limit[] = {1810000, 3500000, 7000000, 10100000, 14000000, 18068000, 21000000, 24890000, 28000000}; PROGMEM const uint32_t upper_limit[] = {2000000, 3800000, 7200000, 10150000, 14350000, 18168000, 21450000, 24990000, 28700000}; PROGMEM const uint8_t band_filter[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9}; PROGMEM const char label_0[] = " -- "; PROGMEM const char label_1[] = "160m"; PROGMEM const char label_2[] = " 80m"; PROGMEM const char label_3[] = " 40m"; PROGMEM const char label_4[] = " 30m"; PROGMEM const char label_5[] = " 20m"; PROGMEM const char label_6[] = " 17m"; PROGMEM const char label_7[] = " 15m"; PROGMEM const char label_8[] = " 12m"; PROGMEM const char label_9[] = " 10m"; PROGMEM const char * const band_label[] = {label_0, label_1, label_2, label_3, label_4, label_5, label_6, label_7, label_8, label_9};
lower_limit[] i upper_limit[] to odpowiednio tablice z częstotliwościami dolnych i górnych granic pasm. Pasm może być w zasadzie zdefiniowanych dowolnie dużo. Aby dołożyć pasmo trzeba jego granice dopisać do wymienionych wcześniej tablic, dorobić dla niego etykietkę na wzór którejś z linijek z label_nn[] i dołożyć tą etykietkę do tablicy band_label[].
Sterowanie filtrami zrealizowane jest za pomocą dekodera 4028, więc filtry mają numery od 0 do 9. Tablica band_filter[] służy do przypisania każdemu pasmu filtra o odpowiednim numerze. W tym miejscu należy zwrócić uwagę na istotny szczegół – otóż numery pasm to zupełnie inna rzecz niż numery filtrów. Pasmo o numerze 0 zarezerwowane jest do oznaczenia częstotliwości, które nie mieszczą się w żadnym ze zdefiniowanych pasm. Z tego powodu pierwsza pozycja tablicy band_filter[] przeznaczona jest na numer „filtru” typu bypass – może to być albo zwykła zwora, albo jakiś LPF. Ja w swojej konfiguracji wybrałem dla tego filtru numer 0, ale każdy może sobie to ustalić tak, żeby pasowało do posiadanej płytki filtrów. Pozostałym pasmom można przypisywać dowolne filtry.
W ten sposób nie ma już problemu żeby dołożyć np. pasmo CB tak, żeby było obsługiwane przez filtr z pasma 10m i miało swoją własną etykietkę na wyświetlaczu. Jest to być może trochę skomplikowane, ale mam nadzieję, że będzie to na tyle elastyczne i uniwersalne rozwiązanie, że zadowoli znaczną większość potencjalnych użytkowników.
Obsługa
Obsługa sterownika powinna być raczej intuicyjna. W normalnym trybie pracy enkoder powoduje zmianę częstotliwości generowanego sygnału. Krok przestrajania wyświetlany jest w prawym dolnym rogu ekranu, a zmienia się go cyklicznie przez naciśnięcie przycisku enkodera.
W środkowej części dolnego wiersza wyświetlana jest informacja o pasmie, w którym znajduje się aktualna częstotliwość. Jeśli częstotliwość ta nie mieści się w żadnym ze zdefiniowanych pasm, wyświetlane jest „–” co sygnalizuje, że włączony jest filtr „bypass”.
Wciśnięcie przycisku BUTTON_1 powoduje wejście do trybu przywracania pamięci (Memory Recall). W trybie tym w lewym dolnym rogu ekranu wyświetlany jest numer komórki pamięci. Następująca po nim literka „r” przypomina, że jesteśmy w trybie przywracania, a nie zapisu. Wyświetlacz pokazuje zapisaną w danej komórce częstotliwość i odpowiadające jej pasmo. Pomiędzy komórkami poruszamy się za pomocą enkodera. Ponowne wciśnięcie przycisku BUTTON_1 powoduje ustawienie częstotliwości z aktualnej komórki pamięci i powrót do normalnego trybu pracy. Wciśnięcie zaś przycisku BUTTON_2 powoduje opuszczenie trybu przywracania pamięci bez żadnych zmian.
Tryb zapisu pamięci (Memory Save) uruchamiany jest przyciskiem BUTTON_2 i oznaczony jest literką „s” przy numerze komórki pamięci. W trybie tym mamy możliwość zapisania bieżącej częstotliwości w wybranej komórce pamięci. Ponowne wciśnięcie przycisku BUTTON_2 porzuca tryb zapisu, natomiast wciśnięcie przycisku BUTTON_1 zatwierdza operację i wraca do normalnego trybu pracy.
autor: Konstantinos, SV1ONW
04 Mar 2015 o godz. 20:12
Hello again dear friend.
Did you have some time to look over my question I posted to you?
Thanking you in advance,
73
Konstantinos
autor: sq9nje
06 Mar 2015 o godz. 14:24
Hi Konstantinos,
Unfortunately I didn’t receive any of your previous messages.
73
Przemek
autor: Željko-9A3RU
28 Kwi 2015 o godz. 22:24
Hello Przemek!
I find your code for SDR, but when i verify code…have a bunch of error!!
Please, can you again investigate your code,because i will include them for my new SDR TRX!
Also,have you this code on GitHube?
All the best from Croatia!
Željko-9A3RU
autor: Amogh Desai
07 Mar 2016 o godz. 11:25
Hi,
There have been a lot of changes made to the Si5351 library and that is reason other users are getting errors while verifying the code in Arduino IDE.
Could you please update the code with such that it works with the current SI5351 library ??
Regards,
VU2DES
Amogh
autor: sq9nje
07 Mar 2016 o godz. 13:16
Hi Amogh,
The project that I published actually uses my own Si5351 library available on GitHub. It’s mentioned in the article. I know that the Adafruit and NT7S libraries have progressed far ahead since I published this but I don’t have any time to refactor the code. Unfortunately you need to treat this AS IS and do any modifications you need yourself.
73,
Przemek SQ9NJE
autor: Marcin SP5IOU
10 Gru 2016 o godz. 00:59
Hej.
Zrobiłem ten układ na płytce stykowej.
Musziałem w kodzie poprawić częstotliwość zegara Si5351 bo w moim module jest 25MHz.
Właściwie to wszystko działa, ale ze wzrostem częstotliwości, sygnał z Si5351 zmienia się z prostokąta coraz bardziej na sinusoidę, jednocześnie zmniejsza się napięcie wyjsciowe do wartości poniżej progu zadziałania kluczy w Pilgrimie.
Czy to powszechne zjawisko, czy tylko dotyczy mojego modułu Si5351 Adafruit?
autor: sq9nje
10 Gru 2016 o godz. 09:02
Hej,
Jakim przyrządem obserwujesz ten sygnał? Przy jakiej częstotliwości zmienia się w sinusoidę?
Pamiętaj, że sygnał prostokątny jest bogaty w harmoniczne i aby poprawnie „oddać jego kształt” oscyloskop musi mieć dużo szersze pasmo przenoszenia niż częstotliwość podstawowa Twojego sygnału. Przy wysokich częstotliwościach trzeba też pamiętać, że pojemność sondy powoduje, że wejście oscyloskopu nie ma wcale tak wysokiej impedancji jak by się mogło wydawać.
autor: Marcin SP5IOU
10 Gru 2016 o godz. 01:01
Nie działa wpisywanie do pamięci.
Wpisuje sie 0 – zero
Odczyt wygląda na ok.
autor: stanisław
01 Paź 2017 o godz. 21:45
Witam nie mogę skompilować programu .Proszę o pomoc
73! SP3JHN
autor: charudatt
13 Cze 2018 o godz. 19:00
It compiles properly, thank you. Guys, please use his libraries and do not upgrade the Libraries.
Thank you for the share.
vu2upx