wtorek, 27 grudnia 2016

Życie "jedynek" - czyli najprostszy, probabilistyczny, jednowymiarowy automat komórkowy

Automaty komórkowe to niewyczerpane źródło inspiracji dla programistów, fizyków, matematyków, a także komputerowych artystów (więcej teorii u "cioci Wikipedii" i u "wujka Google" )
Zanim jednak będziemy potrafili zaprogramować te najbardziej znane, musimy poćwiczyć na najprostszych. Choć efekty nie będą tak spektakularne.

Poniższy przykład w sposób czysto losowy zmienia wartość w komórce jednowymiarowej tablicy na 1, i ze znacznie większym prawdopodobieństwem na 0. Czas, czyli kolejne kroki automatu są prezentowane w kolejnych liniach pikseli okna, od góry do dołu, zatem pionowe białe linie reprezentują "życie" pojedynczej jedynki.


Sam kod automatu jest bardzo prosty, ale służy nam przy okazji do prezentacji użycia tablicy w Processingu, której tworzenie jest zawsze "dynamiczne" (operator new), odmiennie od tego co można spotkać w takich językach jak C, Pascal czy Fortran. Premią za to jest możliwość sprawdzenia w każdej chwili rozmiaru tablicy za pomocą jej właściwości lengh.


Manipulując prawdopodobieństwami urodzenia i śmierci (żółte ramki) możemy uzyskać różną gęstość zasiedlenia tablicy świata, a więc różną gęstość i typową długość linii życia.

środa, 21 grudnia 2016

Wykres funkcji dwu zmiennych

Poniższy program realizuje wykres funkcji zależnej od dwu zmiennych. Żeby uniknąć niewątpliwie trudnego programowania grafiki 3D wartość funkcji przedstawiamy za pomocą koloru punktu - trochę podobnie jak na mapie, tylko bez poziomnic.

Wadą tej wersji jest brak podglądu w trakcie rysowania, które może trwać dosyć długo. No i brak możliwości łatwej modyfikacji do rysowania innej funkcji. Tych wad nie ma już kolejna wersja:
Teraz już można modyfikować wizualizowaną funkcję a także rozmiar okna. Poniżej wynik dla funkcji: cos x * cos (y*y):
Miłej zabawy :-)




niedziela, 18 grudnia 2016

Prosty wykres funkcji sinus

Program rysuje wykres funkcji sinus w prosto zaznaczonym układzie współrzędnych
(w trybie bez procedur i animacji - w oknie widać dopiero ostateczny wynik)


Można też skopiować z konsoli dokładne wyniki liczbowe.

Ten sam niemal program w wersji proceduralnej, ale także bez animacji. Dodanie proceduralności pozwala zdefiniować własną funkcję trygonometryczną  w tym wypadku sin 2x

-  .

sobota, 3 grudnia 2016

Błądzenie - ruchy Browna

Zaimplementujemy dzisiaj model stricte fizyczny - będą to dyfundujące cząsteczki. Jednak na początek zbadany pojedynczą cząstkę, dopiero potem przejdziemy do większej liczby.
Oto program na pojedynczą błądzącą cząsteczkę. Jest to uproszczenie jednej z wersji programu "Bila".
W linii 11. wyłączamy "wygładzanie", co nam zagwarantuje, że jeśli cząstka zniknie z ekranu w danym miejscu, to na dobre - nie pozostanie po niej żaden ślad. Jak już program będzie działał, możecie sprawdzić co by było, gdyby tą linię wykomentować.
Początkowe położenie cząstki to środek okna (linia 12.). Rysowanie w odcieniu szarości zależnym od licznika kroków count (zdefininiowanego w linii 17.) odbywa się na początku procedury draw().
Właściwy model, czyli zmiana położenia cząstki zaczyna się od linii 26.
Nie dokonujemy od razu przypisania na zmienne x i h, ale definiujemy dwie nowe zmienne newx i newh którym przypisujemy wartości obliczone jako poprzednie położenie zmodyfikowane o wartość losową z zakresu -maxd..maxd (linie 26. i 27.)>
Potem sprawdzamy czy wyliczone wartości nie są położeniem poza oknem i odpowiednio je modyfikujemy, a dopiero potem przypisujemy na zmienne x i h zmieniajac realnie położenie "cząsteczki".

Zmiana z jednej cząsteczki na wiele jest w zasadzie "kosmetyczna" ;-) (poniżej)
Zmienne x i h stają się jednowymiarowymi tablicami o rozmiarze Size mówiącym ile mamy jednocześnie cząsteczek w oknie.
Reszta zmian w kodzie jest prostą konsekwencją tego faktu:
 

 Wszystkie cząsteczki nie mogą być w jednym miejscu - w środku, stąd losujemy ich pozycje początkowe z zakresu 0..500 w pionie i w poziomie (linie 13..17).
Musimy też jakoś rozróżniać poszczególne cząsteczki, stąd uzależnienie koloru od indeksu cząsteczki przy wyświetlaniu (linia 27.).

W warunkach ograniczania "pudełka" nie musimy nic zmieniać, jedynie przypisania w liniach 59. i 60. W tej wersji jednak wędrujące cząsteczki pozostawiają za sobą ślad, co daje ciekawy efekt graficzny, ale szybko przestaje mieć cokolwiek wspólnego z procesem fizycznym, który mieliśmy modelować. Dlatego musimy poprzednie pozycje cząsteczek wygaszać kolorem tła (linie 55-60.)

Skoro jednak kompletna wizualizacja odbywa się na końcu pętli zmiany stanu, to osobnej pętli wizualizacyjnej z początku funkcji draw() możemy się już pozbyć.


niedziela, 20 listopada 2016

Ruch 2D - błądzenie bili, modyfikacja kodu

Modyfikacja funkcji draw() polega na zmianie warunku instrukcji if() zajmującej się zmianą prędkości oraz powiązaniu zmiany prędkości ze zmianą koloru
Zależy nam na tym żeby zmiana prędkości zachodziła ŚREDNIO raz na sekundę ale nieregularnie. Funkcja random() w Processingu zwraca zawsze wartość zmiennoprzecinkową typu float. Jeśli parametrem jest FR to będzie to wartość zmiennoprzecinkowa z zakresu <0..FR>. Taka wartość bardzo rzadko będzie dokładnie równa 0, ale całkiem często będzie z zakresu <0..1). Dlatego używamy funkcji floor(), która odcina część ułamkową i liczby zmiennoprzecinkowej.
Dzięki temu z prawdopodobieństwem 1/FR dostajemy 0 i ciało złożonej instrukcji warunkowej się wtedy wykonuje.

Ruch 2D - błądzenie bili - kod.

Dwa wymiary wymagają dwóch zmiennych definiujących położenie i dwóch definiujących aktualną prędkość. Maksymalna prędkość może być wspólna dla obu wymiarów, podobnie jak współczynnik utraty energii przy odbiciu.

Dzięki zliczaniu klatek i operacji modulo (% reszta z dzielenia całkowitego) możemy, używając funkcji random() losować nowy wektor prędkości (prawie) dokładnie raz na sekundę.
Zwróćcie uwagę że przy zderzeniu odwracamy tylko jedną składową prędkości "upuszczając" jej nieco energii, oraz poprawiając współrzędną kulki tak aby nie przeszła na wylot przez ścianę.
Trochę to naciągana fizyka, ale każdy model musi być uproszczony, a tym bardziej w grach i zabawach :-)

#random

Ruch 2D - bładzenie przypadkowe

Przechodzimy do ruchu w dwu wymiarach.
Poniżej efekty uproszczonego błądzenia losowego kulki.
Zastanówcie się jak to zrobić. Kod będzie w następnym poście...