Dziś zajmę się portem ARexxa w programach używających MUI. Jak łatwo się
domyślić również w tej dziedzinie MUI oferuje daleko idące ułatwienia. Idące
tak daleko, że MUI tworzy port ARexxa za nas i dodatkowo znacznie ułatwia
dodawanie własnych komend. Każdy program ma zestaw standardowych komend
obsługiwanych automatycznie przez MUI. Komend tych jest pięć i pełnią
następujące funkcje:
QUIT - umożliwia zamknięcie programu,
HIDE - ikonifikacja programu,
SHOW - odikonifikowanie programu,
INFO - pokazuje informacje o programie umieszczone przez programistę w atrybutach takich, jak MUIA_Application_Title, MUIA_Application_Author itp.
HELP - bardzo interesująca komenda, zapisuje do pliku o podanej nazwie wszystkie obsługiwane przez program komendy ARexxa.
Bardziej szczegółowy opis tych komend znajduje się w dokumentacji użytkownika MUI. Tu przyjrzymy się bliżej jedynie komendzie HELP, dzięki której możemy sprawdzić jakie komendy obsługuje program, do którego np. nie mamy dokumentacji. Oprócz samych nazw komend HELP wypisuje wzorzec parametrów. Wzorzec ten oparty jest na tych samych regułach, co wzorce parametrów programów w AmigaDOS. Na rysunku widzicie przykładowy skrypt korzystający z komendy HELP i zapisujący wykaz komend do pliku "RAM:plik". Skrypt jest prościutki, kilka słów wypada wszakże poświęcić nazewnictwu portów. Nazwa portu programu ustalana jest przez atrybut MUIA_Application_Base, do tego dochodzi kropka i numer jednej z (być może) uruchomionych kopii programu. Oczywiście najczęściej nazwa portu kończy się na ".1", niemniej pisząc jakieś poważniejsze skrypty do publicznego użytku warto pamiętać, że ta jedynka wcale nie jest na 100% pewna. Na rysunku poniżej pokazałem wynik działania naszego skryptu. Najpierw wypisane są komendy standardowe (komendy ACTIVATE i DEACTIVATE odpowiadają w działaniu odpowiednio SHOW i HIDE), a następnie komendy specyficzne dla danego programu. W naszym przykładzie są to komendy "SetColor" i "GetColor". Komenda "GetColor" nie ma żadnych parametrów, komenda "SetColor" natomiast posiada trzy parametry, każdy z nich jest liczbą (modyfikator "/N"), i żaden z nich nie może być pominięty (modyfikator "/A"). Przypominam, że pełny opis modyfikatorów używanych we wzorcach parametrów znajduje się w autodoku do funkcji ReadArgs() z dos.library.
Teraz przejdę do omówienia sposobu dodawania własnych komend ARexxa. Najważniejszym atrybutem jest tu MUIA_Application_Commands. Jego wartością powinna być tablica struktur MUI_Command:
struct MUI_Command { STRPTR mc_Name; STRPTR mc_Template; LONG mc_Parameters; struct Hook *mc_Hook; LONG mc_Reserved[5]; };
Każda struktura opisuje jedną komendę i zawiera 4 pola (są jeszcze pola "reserved", ale te nas nie interesują). Na początek mamy wskaźnik na łańcuch tekstowy będący nazwą komendy. Kolejny wskaźnik wskazuje na omówiony wyżej wzorzec parametrów. Następnie mamy ilość tych parametrów. Jeżeli komenda może być wywołana z różną ilością parametrów (bo nie wszystkim daliśmy modyfikator "/A" we wzorcu), należy tu podać maksymalną ilość parametrów. Ostatnim polem struktury jest adres struktury Hook odpowiadającej hookowi który ma być wywołany dla tej komendy ARexxa. Tablicę komend należy zawsze zakończyć strukturą pustą, zawierającą same zera.
Wykonanie komendy odbywa się więc w hooku. Przed wywołaniem hooka MUI przeprowadza analizę parametrów zgodnie z podanym wzorcem, parametry numeryczne są zamieniane na liczby. Jeżeli podane parametry nie odpowiadają wzorcowi, MUI zwraca kod błędu w zmiennej ARexxa RC, a hook nie jest wywoływany. Przy prawidłowych parametrach MUI umieszcza adres obiektu aplikacji w rejestrze a2 procesora, a adres tablicy parametrów w rejestrze a1. Zwracam uwagę na ważną różnicę - w przypadku parametrów numerycznych w tablicy znajdują się same parametry, zmienna umieszczana w a1 jest więc typu "(long [])*" albo, korzystając z równoważności tablicy i wskaźnika, "long**". W przypadku parametrów tekstowych w tablicy mamy adresy łańcuchów, odpowiednim typem jest więc "((char*)[])*" lub "char***". W przypadku mieszanych parametrów nie obejdzie się bez rzutowania typów tu i ówdzie.
Każda komenda ARexxa zwraca wynik swojego wykonania w zmiennej RC (służącej głównie do informowania o błędach), oraz może zwrócić wynik tekstowy w zmiennej RESULT. RC obsługujemy w bardzo prosty sposób - do tej zmiennej przekazywana jest wartość zwracana na wyjściu z hooka (przeważnie jest to zero). Kontrolę nad zmienną RESULT daje nam natomiast atrybut MUIA_Application_RexxString. Ustawiamy go po prostu na adres łańcucha tekstowego, jaki chcemy przekazać do RESULT. Łańcuch ten może być zmienną lokalną (tak jest w hooku obsługującym komendę GetColor w przykładzie), gdyż MUI wykonuje jego kopię.
W ten sposób doszliśmy do dzisiejszego przykładu. Można powiedzieć, że jest to programik wzbogacający ARexxa o możliwość wybrania koloru RGB za pomocą GUI. Można sobie wyobrazić jego zastosowanie w skryptach np. do programów graficznych, albo generujących strony WWW. Program korzysta z klasy MUIC_Coloradjust. Klasa ta tworzy kompletny obiekt wyboru koloru zawierający suwaki RGB, oraz gadżety BOOPSI: colorwheel i gradientslider. Oprócz tego po lewej znajduje się pole pokazujące aktualnie wybrany kolor. Niestety pole to jest aktywne tylko wtedy, gdy ekran posiada wolne miejsca w tablicy kolorów. Na rysunku pokazany jest wygląd programu uruchomionego na oddzielnym ekranie w 256 kolorach. Oczywiście najlepiej klasa ColorAdjust spisuje się na ekranach 16- i 24-bitowych. Komenda "SetColor" naszego przykładu pozwala na ustawienie składowych RGB, natomiast "GetColor" przekazuje ustawione składowe w zmiennej RESULT jako liczby rozdzielone spacjami. Rysunek przedstawia efekt działania przykładowego skryptu "pobierz_kolor.rexx" dla koloru ustawionego tak jak na rysunku powyżej. Tak jak zwykle program wraz z kodem źródłowym oraz skrypty ARexxa znajdziecie tutaj.