Idealne przenikanie

25

Trudno mi opisać ten problem słowami, dlatego nakręciłem film (45 sekund), aby go zilustrować. Oto podgląd pytań, spójrz na to na Vimeo: http://vimeo.com/epologee/perfect-crossfade

Przy użyciu liniowego przejścia obrazu powstały obraz będzie miał „spadek” przezroczystości.  Jak mogę temu zapobiec?

Problem tworzenia bezproblemowego przenikania lub rozpuszczania dwóch obrazów lub kształtów powtarzał mi się w wielu dziedzinach w ciągu ostatniej dekady. Najpierw w edycji wideo, potem w animacji Flash, a teraz w programowaniu na iOS. Kiedy zaczniesz googlować, istnieje wiele obejść, ale tym razem naprawdę chcę rozwiązać ten problem bez włamania.

Podsumowanie:
Jak nazywa się technika lub krzywa, która ma być stosowana przy przenikaniu dwóch półprzezroczystych map bitowych o tym samym kolorze, jeśli chcesz, aby wynikowa przezroczystość była zgodna z oryginałem jednego?

Czy istnieje funkcja (matematyczna) do obliczania niezbędnych wartości częściowej przezroczystości / alfa podczas zanikania?

Czy są języki programowania, które mają te funkcje jako preset, podobne do ease in, ease outlub ease in outfunkcje znalezione w języku ActionScript lub kakao?

Aktualizacja: Oprócz wideo stworzyłem przykładowy projekt (wymaga Xcode i iOS SDK) i opublikowałem go na github. Pokazuje tę samą animację co wideo, ale tym razem z kwadratami: https://github.com/epologee/StackOverflow-Example-Code

epolog
źródło
7
Nic o tym nie wiem, ale +1 do filmu.
sebastiangeiger
Zależy od sposobu implementacji operatora over. Zobacz en.wikipedia.org/wiki/Alpha_channel
artistoex
Zgadzam się, @artistoex, jest coś w tym nad operatorem, dzięki za link! Jednak jeśli odpowiedź jest gdzieś tam zakopana, nie widzę jej :(
epolog
Matematyczna reprezentacja operatora ponad prowadzi do równania. Przykład nad operatorem: C = alfa * c1 + (alfa-1) * c2 daje alfa = (C + c2) / (c1 + c2) (C jest wynikiem zmieszania dwóch kolorów c1, c2). Oznacza to, że dla tego operatora nie ma żadnej funkcji, która spełnia twój warunek.
artistoex,
Dla C = alpha1 * c1 + alpha2 * c2 (0 <= alpha1, alpha2 <= 1) istnieje taka funkcja: alpha1 = (C-alpha2 * c2) / c1.
artistoex,

Odpowiedzi:

3

Nie wiem, jak mogłaby się nazywać w dziedzinie edycji wideo, ale nazwałbym krzywą krzywą S lub krzywą sigmoidalną . Stworzenie efektu przenikania, którego szukasz w systemie iOS, powinno być bardzo proste, korzystając z funkcji kCAMediaTimingFunctionEaseInEaseOut Core Animation . Wystarczy animować alphawłaściwość dwóch widoków w przeciwnych kierunkach (jeden 0-> 1, jeden 1-> 0) za pomocą tej funkcji pomiaru czasu:

[UIView beginAnimations:@"crossfade" context:nil];
[UIView setAnimationDuration:1.0];
[UIView setAnimationCurve:UIViewAnimationCurveEaseInOut];
view1.alpha = 0.0;
view2.alpha = 1.0;
[UIView commitAnimations];

Uwaga: Naprawdę powinieneś używać metod animacji opartych na blokach zamiast wygodnych metod UIView. Użyłem powyższych metod UIView, ponieważ jest to bardzo łatwe do zrozumienia i łatwe do pisania z pamięci. Korzystanie z bloków nie jest jednak dużo trudniejsze.

Dodatek: Jeśli nie podoba Ci się UIViewAnimationEaseInOut, możesz utworzyć własną funkcję pomiaru czasu opisaną w rozdziałach Czas, Przestrzenie czasowe i CAAnimation . Jest to nieco bardziej zaawansowane niż prosta animacja pokazana powyżej, ale daje Ci pełną kontrolę, jakiej potrzebujesz.

Caleb
źródło
Sigmoid! To już o krok bliżej, dzięki! Podany fragment kodu nie działa od razu, ponieważ setAnimationCurve przyjmuje inny parametr niż kCAMediaTimingFunctionEaseInEaseOut. Miałeś na myśli UIViewAnimationCurveEaseInOut? Problem z tą krzywą jest jednak taki sam (spadek na środku), ponieważ w dowolnym momencie dwie wartości alfa w prostym dodaniu będą równe 1.0, gdzie jak w mojej ręcznie wyregulowanej krzywej trzeba ją przekroczyć, 1.0aby uzyskać pożądane wyniki .
epolog
Rozumiem teraz ... masz rację co do stałej - zaktualizowałem kod w odpowiedzi. Dodałem również link do dokumentów, które wyjaśniają, jak tworzyć własne funkcje pomiaru czasu.
Caleb
Moje animacje wykonuję z bloków, ale istota jest taka sama. Wbudowane krzywe nadal nie mają zastosowania, ze względu na ich symetrię, ale dodatek utorował drogę do niestandardowej funkcji CAMediaTimingFunkcji, która pasowała do tej, której użyłem w filmie After Effects. Problem polega na tym, że nie ma jednej krzywej sigmoidalnej, która pasowałaby do każdego scenariusza , różne początkowe poziomy krycia będą wymagały różnych pozycji Beziera, aby pozbyć się „zanurzenia”. Coś mi brakuje.
epolog
Cześć @Caleb, zamieściłem przykładowy projekt na GitHub (patrz post). Niestandardowy czas jest pomocny, ale jeśli zmienisz initialTransparencywartość, nie ma sensu. Nie miałbyś pojęcia, co dalej?
epolog
2
Jeszcze kilka drobiazgów, które pomogą w wyszukiwaniu w Google; programiści graficzni nazywają wykres, że mówisz o „gładkim kroku”. Programiści o dużej matematyce często nazywają to „pustym interpolatorem”. A prostym równaniem do obliczenia jednego bez trygonometrii jest: „3t ^ 2 - 2t ^ 3”.
Trevor Powell,
1

W grafice komputerowej ta funkcja nazywa się gładkim krokiem . W przypadku płynnego przenikania określa globalną wartość alfa kompozycji.

Jeśli obrazy wejściowe mają kanał alfa, najpierw upewnij się, że alfa jest wstępnie pomnożone . Następnie możesz wykonać kompozycję crossfade od razu, korzystając z płynnego przejścia alphana każdym kanale [ X = A*alpha + B*(1-alpha)] i oczekiwać rozsądnych rezultatów.

nadchodząca burza
źródło
0

Możesz użyć funkcji rozkładu wykładniczego:

Alpha1(time) = 1 - exp(-time / (0.2 * transitionTime)); // fade in
Alpha2(time) = 1 - Alpha1(time); // fade out

Twój wykres wygląda bardziej jak:

Alpha1(time) = sin(time * 0.5 * pi / transitionTime); // fade in
Alpha2(time) = cos(time * 0.5 * pi / transitionTime); // fade out
Danny Varod
źródło
Dzięki @Danny. Właściwie, wykonanie 1 - Alpha1(time)równania nie zajmie się zapadnięciem, ponieważ dwa zmieszane obrazy 0,5 alfa nie dadzą złożonego obrazu z 1,0 alfa. Narysowane przeze mnie niestandardowe krzywe nie są odbijane pionowo.
epolog
1
1-alfa był dla rozkładu wykładniczego, który moim zdaniem jest bardziej odpowiedni. Jednak w przypadku funkcji sin / cos sin (t) = sqrt (1-sqr (cos (t)) jednak obliczanie każdego z nich osobno powinno być szybsze.
Danny Varod 16.11.11
Gdyby problemem było to, jak mogłaby wyglądać funkcja podobnej krzywej, matematyka jest poprawna. Problem polega jednak na tym, jak poradzić sobie z mieszaniem dwóch kolorów, np. Jak uzyskać 40% niebieski + 40% niebieski, aby uzyskać 80% niebieski.
epolog
Jest to łatwe do zrobienia, ale spowodowałoby źle wyglądające nasycenie, gdy suma kolorów> 100%.
Danny Varod,