Posts tagged ‘game development’

Techdema: za i przeciw

2007-09-22 13:49

Zakończyłem ostatnio pewien etap w tworzeniu silnika, czyli prace nad własnym systemem graficznego interfejsu. Taka okazja jest dość dobra dla wykorzystania napisanego już kodu i złożenia z niego tzw. techdema.
Takie demo nie jest naturalnie tym samym co wersja demonstracyjna gry (na przykład dlatego, że chwilowo żadnej gry nie piszę :)) czy demo scenowe. Jego celem jest prezentacja aktualnych możliwości silnika lub jakiegoś fragmentu jego funkcjonalności.

Czy jest sens pisania takich dem? Jak zwykle można podać przynajmniej kilka argumentów przemawiających tak za, jak i przeciwko. In plus możemy zaliczyć techdemom, że:

  • pozwalają sprawdzić napisany kod poprzez użycie go w rzeczywistej aplikacji
  • można dzięki nim przekonać się, czy interfejs danego modułu czy silnika w ogóle odpowiada naszym oczekiwaniom – czyli czy jest wygodny, elastyczny, itp.
  • pisząc je, jest się potem czym pochwalić :)

Tyle zalet. Są też jednak argumenty drugiej strony, iż:

  • jeżeli kod jest systematycznie i na bieżąco testowany, napisanie dema nie pomaga za bardzo w wykryciu w nim ewentualnych nowych błędów
  • powstały program (czyli demo) jest zazwyczaj bezużyteczny z praktycznego punktu widzenia zarówno dla “użytkownika” (który może sobie co najwyżej pochodzić po trójwymiarowym terenie, poklikać tu i tam, czasem próbować ustawiać różne parametry), jak i programisty – zwłaszcza jeśli demko ma tylko ładnie wyglądać, a nie np. testować wydajność

A dodatkowo tworzenie dem, publikowanie screenów i tym podobne działania są przejawem tej silnikologii, do której, szczerze mówiąc, nie jestem jeszcze tak do końca przekonany :) Ale to już temat na inną okazję.
W każdym razie dopóki nie zajmę się na poważnie grafiką 3D i dopóki nie będzie w tej dziedzinie widać jakichś efektów, nie mam chyba za bardzo się czym chwalić ;P

Tags: ,
Author: Xion, posted under Thoughts » 4 comments

System GUI #7 – Pole tekstowe

2007-09-16 21:16

Wśród standardowych kontrolek spotykanych w każdym systemie graficznego interfejsu jest jedna, która zdecydowanie wyróżnia się stopniem skomplikowania. Z wierzchu to tylko mały, podłużny prostokąt z wpisanym ciągiem znaków, który można modyfikować. Jednak mechanizmy sprawiające, że jest to możliwe, nie są wcale takie proste.
Mówię tu oczywiście polu tekstowym, znanym też jako textbox, editbox lub po prostu edit.

Powodów, dla których właśnie ta kontrolka wyróżnia się złożonością, jest przynajmniej kilka. Są to chociażby:

  • Kontrolowanie, jaki fragment tekstu jest w aktualnie widoczny w ramach kontrolki. Jak wiemy, pole tekstowe powinno oferować możliwość wpisywania tekstu dłuższego (pikselowo) niż jego rozmiary, dlatego często część jego zawartości będzie niewidoczna. Należy jednak zapewnić możliwość przewijania (klawiszami strzałek wraz z Ctrl oraz Home i End), aby możliwe było ukazanie innego fragmentu tekstu.
  • Przycinanie w polu tekstowym

  • Obsługa kursora tekstowego, czyli tzw. karetki. Oprócz przesuwania za pomocą klawiatury użytkownik bardzo słusznie będzie oczekiwał, że jest to możliwe także poprzez kliknięcie myszą. Wymaga to więc istnienia sposobu na określenie, w jaki znak użytkownik trafił. A poza tym karetka musi jeszcze mrugać odpowiednio zachęcająco – w końcu dawniej nazywała się ona znakiem zachęty :)
  • Pole tekstowe z kursorem (karetką)

  • Możliwość zaznaczania tekstu. Tradycyjnie jest to możliwe poprzez przeciąganie, jak również z klawiatury (z użyciem klawisza Shift). Kontrola stanu zaznaczenia to generalnie niezbyt złożona, ale też nie tak trywialna maszyna stanów
  • Zaznaczenie w polu tekstowym

Tak naprawdę choćby w systemie Windows pola tekstowe umożliwiają nieco więcej, jak na przykład możliwość cofnięcia ostatniej operacji, obsługa Schowka czy nawet menu kontekstowe. Takie cuda nie są chyba jednak potrzebne do szczęścia :)
Zauważmy też, że kontrolka umożliwiająca edycję dłuższego tekstu dzielonego wiersza to coś zupełnie innego niż zwykły textbox i jej możliwości są nieporównywalnie większe. Dochodzą tam bowiem paski przewijania, zaznaczanie rozciągnięte na kilka wierszy, i tak dalej.

Implementując proste pole tekstowe zauważyłem, że bardzo pomaga przy tym odpowiednia konstrukcja pewnych podstawowych mechanizmów GUI – jak mouse capture czy fokus klawiatury, modelu propagacji zdarzeń oraz modułu odpowiedzialnego za wypisywanie tekstu. Łącznie jednak wychodzi z tego i tak nadspodziewanie duża ilość kodu ze sporą liczbą zagmatwanych ifów :]

Tags: ,
Author: Xion, posted under Programming » 1 comment

Składanie frameworka

2007-09-12 8:57

Kończąc powoli prace nad systemem GUI (a przynajmniej jakimiś sensownymi podstawami tego systemu), zakańczam jednocześnie prace nad “płaską” częścią silnika. Innymi słowy, już wkrótce nie będzie żadnej wymówki i trzeba będzie zabrać się za dodanie upragnionego, a zarazem niezwykle komplikującego życie trzeciego wymiaru :)

Pomyślałem jednak, że najpierw dobrze byłoby poskładać napisane już w cegiełki w sensowną całość i stworzyć coś w rodzaju frameworka. Chodzi tutaj o tę warstwę pośrednią między kodem silnika a użytkownikiem i systemem, czyli szkielet umożliwiający wygodne tworzenie rzeczywistych aplikacji.
W wielu bibliotekach różnie to rozwiązano. Z jednego strony DirectX czy OpenGL zostawiają to całkowicie w gestii programisty. Musi on samodzielnie przygotować chociażby to okienko, w którym będzie się odbywało rysowanie. Z kolei np. SDL bardzo głęboko ingeruje w kod programu, narzucając nawet określoną formę funkcji main.

Najlepsze jest oczywiście takie rozwiązanie, które zapewnia zarówno dużą elastyczność, jak i nie zmusza do napisania kilkuset linijek w celu zobaczenia czegokolwiek. Wydaje mi się, że bliski ideałowi jest pomysł zamknięcia funkcjonalności frameworka w klasę w rodzaju Application, zawierająca metody pozwalające na inicjalizację programu i późniejsze sterowanie nim. Metody tej klasy byłyby wywoływane w funkcji startowej programu, czyli main lub WinMain. Tak to wygląda na przykład w Windows Forms czy w VCL (Delphi):
[delphi]program SomeProject;

uses
Forms,
MainFrm in ‘MainFrm.pas’ {Form1};

{$R *.res}

begin
Application.Initialize;
Application.CreateForm(TMainForm, MainForm);
Application.Run;
end.[/delphi]
Według mnie najlepiej jest, gdy obiekt głównej klasy programu jest albo statycznie tworzonym singletonem, albo zostaje wykreowany przez programistę przy rozruchu aplikacji. Najważniejsze, aby nie zmuszać do dziedziczenia po klasie Application – po to na przykład, by nadpisując metody wirtualne zapewnić możliwość reakcji na zdarzenia (jak wciśnięcia klawiszy czy ruch myszy). Dzięki delegatom, choćby tym z biblioteki FastDelegate, można to zrobić dokładnie tak, jak w “bardziej cywilizowanych” językach programowania.

Tags: ,
Author: Xion, posted under Programming » 2 comments

System GUI #6 – Pole wyboru i przycisk opcji

2007-09-06 20:09

Zwykłe przyciski (buttons) można tylko wciskać jak guziki na monitorze lub klawisze na klawiaturze. Wydawałoby się, że nie mają one wiele wspólnego z bardziej zaawansowanymi elementami interfejsu: polami wyboru (checkboxes) czy przyciskami opcji (radio buttons).
Te pierwsze to proste przełączniki: mogą być zaznaczone lub nie, swój stan zmieniają po kliknięciu i zazwyczaj odwzorowane są na jakieś funkcje programu, które mogą być włączane i wyłączane. Te drugie oferują z kolei wybór z większej liczby wariantów, z których tylko jeden może być aktywny w danej chwili. Z punktu widzenia użytkownika największa różnica polega jednak na tym, że pola wyboru mają obok etykiet tekstowych kwadraciki, zaś przyciski opcji – kółka :)

Przykład pól wyboru (checkbox) Przykład przycisków opcji (radio button)

Podobieństwo tych dwóch kontrolek do zwykłych przycisków polega na tym, że w identyczny sposób reagują na zdarzenia od myszy – czyli przede wszystkim kliknięcia. Podobieństwo okazało się na tyle duże, że sensowne okazało się połączenie wszystkich tych trzech rodzajów kontrolek wspólną klasą bazową. Nie lubię nadużywania dziedziczenia, ale akurat tutaj rozciągnięcie hierarchii klas wydaje się rozsądne.

Hierarchia klas kontrolek przyciskopodobnych

Z tych trzech typów kontrolek prawdopodobnie najbardziej interesujący jest przycisk opcji, czyli ten z kółeczkiem :) Trzeba bowiem zastanowić się, w jaki sposób zrealizować grupowanie tych obiektów w zestawy, w ramach których tylko jeden radio button może być zaznaczony. Spotkałem tutaj dwa rozwiązania:

  • Wprowadzenie specjalnej kontrolki-kontenera nazywanej zwykle RadioGroup. Kontener ten może zawierać tylko przyciski opcji, które wówczas nawet nie muszą być samodzielnymi kontrolkami (ale cały czas powinny oczywiście sprawiać takie wrażenie). Taka ‘grupa radiowa’ jako pojemnik może, ale nie musi być widoczna na ekranie. Przy takim rozwiązaniu spełniony jest zawsze warunek, że spośród wszystkich przycisków opcji będących bezpośrednio zawartych w jakimkolwiek kontenerze (RadioGroup lub innym) zaznaczony jest tylko jeden.
    Ten wariant występuje na przykład w bibliotece VCL (Delphi).
  • Dodanie do radio buttona właściwości określającej grupę przycisków, jak choćby jej nazwa (napis) lub indeks (liczba). Wtedy należy zapewnić, że zaznaczenie będzie unikalne w ramach przycisków z tego samego kontenera oraz z tej samej grupy.
    To rozwiązanie występuje w Windows Forms.

Ostatecznie zdecydowałem się na wariant drugi. Z punktu widzenia implementacji najważniejszego elementu – czyli dbania o to, by tylko jedna opcja była zaznaczona – oba rozwiązania są bardzo podobne. Tak czy owak trzeba zawsze najpierw odznaczyć wszystkie przyciski, a potem zaznaczyć ten kliknięty. Jest to przy tym jedna z tych sytuacji, w których bardzo ułatwia życie przeklinany operator rzutowania dynamic_cast :]

Tags: , , ,
Author: Xion, posted under Programming » Comments Off on System GUI #6 – Pole wyboru i przycisk opcji

Dziś pomysł, jutro artykuł

2007-08-30 11:04

Wczoraj naszła mnie niesamowita ochota, aby napisać tekst. Taki zwyczajny programistyczny artykuł, w którym można poruszyć ciekawe sprawy i nauczyć czegoś czytelników. Podobne natchnienie ostatnio nie zdarza mi się często, więc żal byłoby go nie wykorzystać :)
Efektem jest dość spory tekst traktujący o pisaniu prostego modułu do grafiki 2D z użyciem DirectX – czyli czegoś, czym zajmowałem się kilka tygodni temu. Jak sądzę wyszedł z tego całkiem przejrzysty i przydatny opis, w którym udało mi się też poruszyć kilka różnych tematów z zakresu DXa ze szczególnym uwzględnieniem dynamicznych buforów wierzchołków.

System GUI #5 – Okno

2007-08-28 17:43

Dawno temu w firmie Xerox wymyślono, że interfejs użytkownika można zapakować w zestaw prostokątnych, nakładających się na siebie okien. Pomysł okazał się niezwykle trafiony i zaowocował nawet wielce kreatywną nazwą pewnego systemu operacyjnego ;) Od tamtej pory trudno sobie wyobrazić zaawansowane UI posługujące się czymś innym niż właśnie zestawem okien.

Nie jest trudno otrzymać na ekranie puste okno. W środowiskach RAD – w rodzaju Visual C# czy Delphi – mamy je najczęściej dane automatycznie, gdy tworzymy nowy projekt. W przypadku programowania niewizualnego (jak np. z użyciem czystego Windows API) sprawa jest nieco bardziej skomplikowana, ale i tak zamyka się w nie więcej niż kilkudziesięciu linijkach.
Takie puste okno wydawać się może mało interesujące czy wręcz zbyt oczywiste, aby zwracać na nie uwagę. Rzadko zwracamy uwagę na to, że ten pozornie trywialny prostokąt sam w sobie potrafi bardzo wiele. Wśród typowych możliwości mamy chociażby:

  • przesuwanie za pomocą przeciągania za pasek tytułu
  • zmianę jednego z wymiarów poprzez przeciąganie brzegów
  • zmianę obu wymiarów poprzez przeciąganie rogów okna
  • Przeciąganie za pasek tytułu okna Zmiana jednego z wymiarów okna Zmiana obu wymiarów okna Przyciski sterujące oknem

  • minimalizacja, maksymalizacja i zamykanie okna przyciskami na pasku tytułu

Uzyskanie podobnej funkcjonalności, zaczynając od zera, jest bardziej pracochłonne niż może się wydawać. W moim przypadku otrzymanie czegoś, co przypomina w pełni funkcjonalne i interaktywne okno, zamknęło się w ok. dwóch tysiącach linijek kodu – nie licząc oczywiście modułu grafiki 2D, potrzebnego do rysowania okien.
To całkiem sporo. Skutkiem ubocznym tej pisaniny jest też to, że obecnie patrzę na stare poczciwe okna systemu Windows z nieco większym respektem :)

Tags: , ,
Author: Xion, posted under Programming » Comments Off on System GUI #5 – Okno

System GUI #4 – Przycisk

2007-08-21 14:48

Co można powiedzieć o czymś tak prozaicznym, jak zwykły przycisk? Ano to, że przycisk jest po to, aby go wciskać :) Od strony użytkownika wygląda to więc bardzo prosto – może nawet zbyt prosto, co czasami kończy się źle, jeśli nie czytamy komunikatów przed pochopnym wciśnięciem OK.
Kwestia oprogramowania takiego tworu jak przycisk, aby zachowywał się zgodnie z oczekiwaniami, jest już jednak trochę trudniejsza.

Przy okazji przycisku wychodzi bowiem kwestia tak zwanego mouse capture, które to pojęcie nie ma dobrego tłumaczenia na język polski. Pozwala ono użytkownikowi rozmyślić się i nie dokonać kliknięcia nawet wtedy, gdy zdążył już wcisnąć przycisk myszki. Wystarczy, że – nie puszczając go – odjedzie kursorem poza obszar kontrolki i tam puści przycisk myszy. Wówczas zarówno zdarzenie wciśnięcia, jak i puszczenia przycisku myszy będzie zarejestrowane, lecz to najważniejsze – kliknięcia – już nie.
Ten dość abstrakcyjny byt mouse capture może być przez kontrolkę posiadany lub nie. Jeżeli kontrolka go posiada, wtedy otrzyma ona informacje o zdarzeniach myszy nawet gdy kursor znajduje się poza jej obszarem. Dzięki temu kontrolka przycisku może być poinformowana o tym, że użytkownik zrezygnował z jej wciśnięcia.

Wciśnięcie przycisku i odjechanie kursorem

Pozostaje jeszcze drobna kwestia graficzna. Otóż w Windows kontrolka przycisku “wyciska się”, jeżeli odjedziemy kursorem poza jej obszar (oczywiście cały czas trzymając wciśnięty przycisk myszki). Kiedy znów wrócimy, wciśnie się ponownie, i tak dalej (ciekawym zalecam własnoręczne eksperymenty ;]). Osobiście nie sądzę, żeby takie zachowanie było bardzo intuicyjne, bo chyba bardziej by mi odpowiadało, gdyby kontrolka pozostała cały czas wciśnięta.
Niestety, nie ja ustanawiam standardy interfejsu, więc postanowiłem się dostosować i zaimplementować windowsowe rozwiązanie :)

Tags: , ,
Author: Xion, posted under Programming » 4 comments
 


© 2017 Karol Kuczmarski "Xion". Layout by Urszulka. Powered by WordPress with QuickLaTeX.com.