Paindemonium Opublikowano 24 Sierpnia 2015 Udostępnij Opublikowano 24 Sierpnia 2015 Witam. Może jest to banalne pytanie ale od jakiegoś czasu z tym walczę. Staram się zrozumieć jak zrobić by obiekty i partykle były rysowane na surface, podłożu czy jak tam leci. Najlepszy przykład to krew. Robię grę top down shooter a raczej na tym typie gry się uczę ją robić. Efekty nie są głupie, coś już działa :). Posiadam też wprowadzoną w formie partykli krew, która leci we wszystkie strony z różną prędkością co fajnie imituje krew. Pytanie brzmi jak zrobić by te owe partykle zostawaiały za sobą trwały ślad niczym w tej dennej gierce Zombie Zoeds (taki syf że głowa boli ale dobry przykład prostego wykorzystania tego efektu).Natrafiłem na coś takiego aczkolwiek z wykorzystaniem obiektów (tu też bym miał pytanie ale zakładam ze zasada jest taka sama z wykorzystaniem surface dla partykli jak i obiektów) . Gość co prawda fajnie tłumaczy ale dość mało konkretnie i przeskakuje trochę kwestii. oraz natrafiłem na troszeczkę konkretów http://forums.tigsource.com/index.php?topic=7441.0 . Oczywiście chciałbym jednak to zrozumieć w dość prosty sposób, od czego zacząć i co przygotować by stworzyć taki efekt. Oczywiście nie jest on tylko na celu by dodać zajefajne rozmazywanie krwi po podłodze ale surface to droga do optymalizacji gry, bo lepiej by na surface był narysowany obiekt niż stał w grze obiekt (np dywan) i zamulał grę, no chyba ze się mylę bo doświadczonym na GM jeszcze nie jestem na tyle by wysnuwać takie wnioski po przejrzeniu wielu tutoriali. Liczę na waszą pomoc i pomysły. Jeżeli będzie taka potrzeba przedstawię kod określonego elementu na którym chcę zaimplementować ten efekt ale najpierw chciałbym poznać konkrety bo nie będę wklejał połowy projektu do posta :). Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Threef Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 Nie jest to łatwe zagadnienie, więc przeniosłem temat do działu "Pytania zaawansowanych". Surface jest najbardziej sensownym i tak na prawdę najłatwiejszym rozwiązaniem. Niestety wymaga od ciebie sporej świadomości co robisz. Musisz pamiętać że surface są przechowywane w pamięci karty graficznej, więc im większa powierzchnia surface tym więcej pamięci zabiera. Surface mniejsze od 1024x1024 będą w porządku. Ogółem najprościej będzie zrobić surface rozmiaru mapy. Wtedy po prostu rysujesz na nim swoją krew. To jest bardzo proste ale musisz umieć obsługiwać surface. Świetne opracowanie tego sposobu masz tutaj w punkcie Debris Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
I am vader Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 Mialem cos wczoraj napisac, ale nie czulem jak sie zabrac za cos rzetelniejszego. Napisze Ci pare informacji, nie beda wystarczyly, ale krok po kroku dojdziesz do tego z pomoca kilku osób(bo wątpie aby jednej osobie chciało się wszystko pisać). Surface to przestrzeń na której rysujesz jak na obrazku czy jak na ekranie. Podstawowo kiedy coś rysujesz, jest to automatycznie rysowane do surface'u aplikacji, czyli powierzchni która jest wyświetlana w oknie gry. W momencie w którym zaczynasz rysować do innego surface'u niż ekran gry, koordynaty gry nie są istotne. W grze pozycja [0,0] to lewy górny róg room'u. W nowym surface, [0,0] to lewy górny róg surface, nie ważne gdzie go chcesz potem narysować. Krok 1: Stwórz surface Aby stworzyć surface musisz skorzystać z funkcji surface_create(szerokosc,wysokosc). Ta funkcja stworzy surface podanych wymiarów i zapisze go w pamięci karty graficznej. Ta druga połowa zdania jest bardzo ważna. Są tutaj 3 rzeczy to zapamiętania: 1.Surface może zostać usunięty przez system, więc jeżeli będziesz chciał się odwołać do nieistniejącego, wywali błąd. 2.Surface należy usunąć kiedy nie będziesz go potrzebował. Jeżeli ten surface ma ślady krwi na mapie, to powinieneś go usunąć, albo chociaż wyczyścić, przechodząc do innego poziomu. 3.Surface zajmie trochę miejsca w pamięci. Tę pamięć możęsz wyliczyć tak: Szerokość * Wysokość * 4 Bajtów. Np. 1024x1024 będzie ważyło 1024*1024*4 = 4194304 Bajtów = 4096 Kilobajtów = 4Megabajty. Gratuluję, wiesz jak policzyć czy nie wysadzisz komuś karty graficznej w powietrze. Kiedy wywołasz funkcję surface_create zwróci ona ID surface'a, więc musisz je sobie zapisać do jakieś zmiennej. GML MojSurface = surface_create(room_width,room_height); //Stworzy surface wymiarow roomu i zapisze jego ID do zmiennej MojSurface</span> Krok 2: Edytuj surface Tutaj podam 4 kluczowe funkcje dla pracy z surface'ami. Rysowanie na surface to jego zmienianie. Jeżeli zastanawiało Cię dlaczego surface jest dobre do śladów krwi, to dlatego, że nie wyczyści się. Normalnie, za każdym razem gdy ekran ma być narysowany, jest on całkowicie czyszczony a następnie wszystkie elementy są na nowo na niego rysowane. Surface się wyczyści tylko kiedy i jeżeli będziesz tego chciał. Aby rozpocząć edycję surface korzystasz z funkcji surface_set_target(ID Surface'a), gdzie w argumencie podajesz nazwę zmiennej w której wcześniej zapisałeś ID surface. Zanim jednak rozpoczniesz pracę nad surface, musisz się upewnić, że nie został usunięty z pamięci(to się może stać jak zminimalizujesz grę). Do tego służy surface_exists(ID surface). Jeżeli surface nie istnieje chciałbyś go wpierw na nowo stworzyć. GML if !surface_exists(MojSurface) then MojSurface = surface_create(room_width,room_height); Tutaj bardzo ważna rzecz do zapamiętania - Kiedy rysujesz na surface, zostaje tak dopóki nie zresetujesz rysowania spowrotem do normalnego. Musisz pamiętać o wyłączeniu rysowania, bo inaczej wszystko się walnie. Do tego służy surface_reset_target(). Oznacza to, że Twoje rysowanie na surface mieści się między surface_set_target(ID) a surface_reset_target(). Ostatnia rzecz przy pracy z surface do zapamiętania, to że kiedy stworzysz surface, nie jest on przezroczysty. Zazwyczaj chcesz aby był, od tego jest funkcja rysowania zwana draw_clear_alpha(0,0) . W twoim przypadku chcesz wyczyścić surface tylko raz - kiedy zostanie stworzony. Chcesz to zrobić tylko raz, ponieważ chcesz się pozbyć nieprzezroczystych czesci surface'a, ale nie chcesz sie pozbywac namalowanych sladow krwi. W tym momencie caly kod wygladalby tak: GML //Create MojSurface = surface_create(room_width,room_height); surface_set_target(MojSurface); //Aktywuj ten surface draw_clear_alpha(0,0); //Wyczysc surface surface_reset_target(); //Wylacz surface</span> GML //Update surface, np. w Step if !surface_exists(MojSurface) //Jezeli surface nie istnieje { MojSurface = surface_create(room_width,room_height); //Stworz go na nowo surface_set_target(MojSurface); //Aktywuj ten surface draw_clear_alpha(0,0); //Wyczysc surface surface_reset_target(); //Wylacz surface } surface_set_target(MojSurface); //Start rysowania //Cos co rysujemy //Jeszcze cos co rysujemy //A tutaj tez cos jeszcze surface_reset_target(); //Koniec rysowania</span> Krok 3: Narysowanie surface w grze Aby surface byl widoczny w grze musisz go narysowac w grze. Robisz to tak samo jak ze spritami i backgroundami. Uzywasz do tego funkcji draw_surface(ID Surface,x,y) Wiecej szczegolow mozesz przeczytac w dokumentacji w GM'ie lub w wersji zamieszczonej online. Uzyteczne linki: 1.Ogólnie o Surface'ach 2.surface_create 3.surface_set_target 4.surface_reset_target 5.draw_clear_alpha 6.surface_exists 7.draw_surface Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Paindemonium Opublikowano 25 Sierpnia 2015 Autor Udostępnij Opublikowano 25 Sierpnia 2015 Super. Biore się dziś do obadania tego. Pytanie jeszcze na boku. To działa tak samo jak inne elementy dodawane do roomu czyli surrface musi być dodany do roomu jako np obj_surface by na tym roomie to działało (tak jak na tym filmiku youtube co podałem)? Z góry dziękuję za wyczerpujące informacje podane w tym temacie :). Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Sutikku Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 Tak, inaczej kod zawarty w obiekcie się nie wykona, skoro nie jest w roomie. Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
I am vader Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 Możesz surface rysować przez istniejący obiekt lub nowy obiekt którego zadaniem może być właśnie pilnowanie tego surface'a, wybór należy do Ciebie. Istotne jest, abyś go rysował w evencie Draw i aby miał DEPTH mniejszy od innych obiektów, bo krew jest przecież pod wszystkim innym, na podłodze. Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Paindemonium Opublikowano 25 Sierpnia 2015 Autor Udostępnij Opublikowano 25 Sierpnia 2015 Super. O wiele więcej kumam z waszych wypowiedzi niż niektórych paplanin tutorialowych na temat surfacu. Mam nadzieję że na tyle to opanuje by zadziałał a potem doszlifowac sprawę by rzeczywiście było to wydajne. Planuje by to coś wyglądało podobnie do tego co mamy w Crimsonland. EDIT: Ok więc wracając jeszcze do fragmentu kodu, który mi zaprezentowaliście a mianowicie: surface_set_target(MojSurface); //Start rysowania //Cos co rysujemy //Jeszcze cos co rysujemy //A tutaj tez cos jeszcze surface_reset_target(); //Koniec rysowania</span> Jeżeli chodzi o Cos co rysujemy itp ttp, to w tym miejscu mam wprowadzić albo jakiś obiekt np sprite z krwią albo obiekt odpowiadający za tworzenie się konkretnych partykli? Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Threef Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 Tak, w tym miejscu masz dodać kawałek kodu który będzie rysował to co chcesz aby zostało narysowane na surface. Czyli np.: draw_sprite_ext() Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
I am Lord Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 Cokolwiek co ma draw_ w nazwie :P Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Paindemonium Opublikowano 25 Sierpnia 2015 Autor Udostępnij Opublikowano 25 Sierpnia 2015 A więc tak. Jest gra, i stworzony obiekt pod nazwą "obj_blood_surface" którego kod wygląda tak: Create: MojSurface = surface_create(room_width,room_height); surface_set_target(MojSurface); draw_clear_alpha(0,0); surface_reset_target(); Step: if !surface_exists(MojSurface) { MojSurface = surface_create(room_width,room_height); surface_set_target(MojSurface); draw_clear_alpha(0,0); surface_reset_target(); } surface_set_target(MojSurface); draw_surface_ext(MojSurface,0,0,1,1,0,130,1); surface_reset_target(); / Sugerowałem się waszym kodem i informacjami z poprzednich tutoriali. Teraz jednak pytanie brzmi co zrobić by to określony obiekt był celem rysowania. Bo w kodzie nigdzie tego nie widze a np obiekt "obj_sp" dodany do mapy odpowiada za tworzenie sie kropek wylatujących od potwora, który dostał hita/zginął. I np chce by te kropki były celem tej operacji, czyli partykle rysowały na surface ślad. Na razie nic mi z tego nie wychodzi a chce na tyle to zrozumieć by potem samodzielnie modyfikować cały surface tak by np elementy pokroju deski na ziemi narysowały swój ślad czy coś by nie zaśmiecać obiektami mapy. Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
I am Lord Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 możesz np dać tym obiektom obj_sp w create: GML surface_set_target(obj_blood_surface.MojSurface); draw_self(); surface_reset_target(); instance_destroy(); Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
I am vader Opublikowano 25 Sierpnia 2015 Udostępnij Opublikowano 25 Sierpnia 2015 surface_set_target(MojSurface); draw_surface_ext(MojSurface,0,0,1,1,0,130,1); surface_reset_target(); To jest niepoprawne. ustawiasz(i resetujesz) target po to aby rysować NA surface. Aby narysować surface sam w sobie, rysujesz go NORMALNIE . Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Paindemonium Opublikowano 28 Sierpnia 2015 Autor Udostępnij Opublikowano 28 Sierpnia 2015 Kumpel musi na to teraz rzucić okiem z którym działam, ja dopiero się tym zajme za tydzien jak wrócę z prac terenowych. Dziękuję wszystkim za pomoc i będziemy się odzywać gdyby dalej dla nas coś było niezrozumiałe. Odnośnik do komentarza Udostępnij na innych stronach Więcej opcji udostępniania...
Rekomendowane odpowiedzi
Jeśli chcesz dodać odpowiedź, zaloguj się lub zarejestruj nowe konto
Jedynie zarejestrowani użytkownicy mogą komentować zawartość tej strony.
Zarejestruj nowe konto
Załóż nowe konto. To bardzo proste!
Zarejestruj sięZaloguj się
Posiadasz już konto? Zaloguj się poniżej.
Zaloguj się