Eski oyunlarda kaybolur. Algoritmanın nasıl türetildiğini bulmak için biraz yardıma ihtiyacınız var


12

Üzgünüm, bu soru biraz ezoterik, ama kafamdan çıkaramıyorum!

Arcade oyunu DoDonPachi (ve diğer birçok eski oyun) kullanılan solmaya algoritması bakıyorum:

resim açıklamasını buraya girin

Birkaç piksel seçmek ve solma süresi boyunca onları izlemek için bir python komut dosyası yazdım. İşte sonuçların temsili bir örneği. Her grubun ilk satırı başlangıç ​​renk değeridir, sonraki her satır geçerli çerçevenin renk değeri ile önceki çerçevenin renk değeri arasındaki farktır.

Starting Value: (132, 66, 189)
Frame 1:    [9, 9, 8]
Frame 2:    [8, 8, 8]
Frame 3:    [8, 8, 8]
Frame 4:    [8, 8, 9]
Frame 5:    [9, 9, 8]
Frame 6:    [8, 8, 8]
Frame 7:    [8, 8, 8]
Frame 8:    [8, 8, 9]
Frame 9:    [9, 0, 8]
Frame 10:   [8, 0, 8]
Frame 11:   [8, 0, 8]
Frame 12:   [8, 0, 9]
Frame 13:   [9, 0, 8]
Frame 14:   [8, 0, 8]
Frame 15:   [8, 0, 8]
Frame 16:   [8, 0, 9]
Frame 17:   [0, 0, 8]
Frame 18:   [0, 0, 8]
Frame 19:   [0, 0, 8]
Frame 20:   [0, 0, 9]
Frame 21:   [0, 0, 8]
Frame 22:   [0, 0, 8]
Frame 23:   [0, 0, 8]
Frame 24:   [0, 0, 0]
Frame 25:   [0, 0, 0]
Frame 26:   [0, 0, 0]
Frame 27:   [0, 0, 0]
Frame 28:   [0, 0, 0]
Frame 29:   [0, 0, 0]

Starting Value: (132, 0, 0)
Frame 1:    [9, 0, 0]
Frame 2:    [8, 0, 0]
Frame 3:    [8, 0, 0]
Frame 4:    [8, 0, 0]
Frame 5:    [9, 0, 0]
Frame 6:    [8, 0, 0]
Frame 7:    [8, 0, 0]
Frame 8:    [8, 0, 0]
Frame 9:    [9, 0, 0]
Frame 10:   [8, 0, 0]
Frame 11:   [8, 0, 0]
Frame 12:   [8, 0, 0]
Frame 13:   [9, 0, 0]
Frame 14:   [8, 0, 0]
Frame 15:   [8, 0, 0]
Frame 16:   [8, 0, 0]
Frame 17:   [0, 0, 0]
Frame 18:   [0, 0, 0]
Frame 19:   [0, 0, 0]
Frame 20:   [0, 0, 0]
Frame 21:   [0, 0, 0]
Frame 22:   [0, 0, 0]
Frame 23:   [0, 0, 0]
Frame 24:   [0, 0, 0]
Frame 25:   [0, 0, 0]
Frame 26:   [0, 0, 0]
Frame 27:   [0, 0, 0]
Frame 28:   [0, 0, 0]
Frame 29:   [0, 0, 0]

Starting Value: (165, 156, 222)
Frame 1:    [9, 8, 8]
Frame 2:    [8, 8, 8]
Frame 3:    [8, 8, 8]
Frame 4:    [8, 9, 9]
Frame 5:    [9, 8, 8]
Frame 6:    [8, 8, 8]
Frame 7:    [8, 8, 8]
Frame 8:    [8, 9, 9]
Frame 9:    [9, 8, 8]
Frame 10:   [8, 8, 8]
Frame 11:   [8, 8, 8]
Frame 12:   [8, 9, 9]
Frame 13:   [9, 8, 8]
Frame 14:   [8, 8, 8]
Frame 15:   [8, 8, 8]
Frame 16:   [8, 9, 9]
Frame 17:   [9, 8, 8]
Frame 18:   [8, 8, 8]
Frame 19:   [8, 8, 8]
Frame 20:   [8, 0, 9]
Frame 21:   [0, 0, 8]
Frame 22:   [0, 0, 8]
Frame 23:   [0, 0, 8]
Frame 24:   [0, 0, 9]
Frame 25:   [0, 0, 8]
Frame 26:   [0, 0, 8]
Frame 27:   [0, 0, 8]
Frame 28:   [0, 0, 0]
Frame 29:   [0, 0, 0]

Starting Value: (156, 90, 206)
Frame 1:    [8, 8, 8]
Frame 2:    [8, 8, 9]
Frame 3:    [8, 8, 8]
Frame 4:    [9, 9, 8]
Frame 5:    [8, 8, 8]
Frame 6:    [8, 8, 9]
Frame 7:    [8, 8, 8]
Frame 8:    [9, 9, 8]
Frame 9:    [8, 8, 8]
Frame 10:   [8, 8, 9]
Frame 11:   [8, 8, 8]
Frame 12:   [9, 0, 8]
Frame 13:   [8, 0, 8]
Frame 14:   [8, 0, 9]
Frame 15:   [8, 0, 8]
Frame 16:   [9, 0, 8]
Frame 17:   [8, 0, 8]
Frame 18:   [8, 0, 9]
Frame 19:   [8, 0, 8]
Frame 20:   [0, 0, 8]
Frame 21:   [0, 0, 8]
Frame 22:   [0, 0, 9]
Frame 23:   [0, 0, 8]
Frame 24:   [0, 0, 8]
Frame 25:   [0, 0, 8]
Frame 26:   [0, 0, 0]
Frame 27:   [0, 0, 0]
Frame 28:   [0, 0, 0]
Frame 29:   [0, 0, 0]

Gördüğünüz gibi, her karedeki her renk bileşeninden 8 veya 9 çıkarılır. Ayrıca, başlangıç ​​renk değeri her renk bileşeni için farklı olsa da, 9 her zaman 8'den sonra üç kare görünür. Ayrıca her renk bileşeninin 8 veya 9'luk bir farkla 0'a (yani siyah) ulaştığına dikkat edin, keyfi bir kalıntı kalmaz. Bu, 8,8,8,9'luk çıkarılan değer döngüsünün asla kırılmadığı anlamına gelir! (Bu algoritma muhtemelen solmanın son karesinin diğerleri kadar pürüzsüz olmasını sağlamak için yazılmıştır.)

Şimdi, bu beni şaşırtıyor. Hesaplamalarıma göre, işlemi tersine çevirirseniz - yani 8,8,8,9 döngüsünü alın ve 29 çerçevedeki tüm olası kombinasyonları bulmak için toplayın - sadece 52 benzersiz sayı elde edersiniz. Ancak olduğu gibi, her renk bileşeni bu setin bir üyesidir! Bu, renklerin bu solma algoritması için özel olarak seçildiği (olası olmayan) veya solma algoritmasının oyunun renk paletinin etrafında tasarlandığı anlamına gelir. Ama nasıl bir yeryüzünde birileri 8,8,8,9 alırsanız, döngüyü uygun şekilde kaydırırsanız ve paletinizdeki her renk bileşeninden sayıları çıkarmaya devam ederseniz, sonunda her bir renk için 0'a ulaşacağınızı nasıl anlayabilirdiniz? ! Kaçırdığım bir matematik hilesi olmalı. Bu ne?


2
Neden sadece alfa ile oynamıyorsun? Fade-in / out animasyonları için böyle yapıyorum.
DogDog

Sadece nasıl türetildiğini anlamaya çalışıyorum, kendi kod algoritması çoğaltmaya çalışmıyorum.
Archagon

Söylediğiniz gibi hissediyorum, renkler 8,8,8,9 dizisine göre seçildi. Bu dizi göz önüne alındığında, 52 * 52 * 52 renk arasından seçim yapabildiler. İlginç bir not, 0'dan başlar ve 8,8,8,9 dizisini eklerseniz 255'e ulaşırsınız. Bu da siyah ve beyaz kullanmalarını sağlar.
Luis Estrada

@Apoc: Solma tarzı alfa solmasından belirgin şekilde farklıdır. Her bir renk değerinin başlangıç ​​değerinin yüzdesi yerine sabit bir sayıya (sayı deseni) nasıl indiğini görüyor musunuz? Bu, daha yaygın yöntemlerde kullanmayı tercih edebileceğiniz durumlar olduğu anlamına gelir. Örneğin retro tarzı.
AlbeyAmakiir

Yanıtlar:


20

Aslında 8-8-8-9 modelinin arkasında basit bir mantık var. Yalnızca 32 yoğunluk seviyesi (bileşen başına 5 bit) kullanırsanız, ancak bunu bileşen başına 8 bit ekranda göstermek istiyorsanız doğal olarak ortaya çıkar.

5-bit yoğunluk seviyesine sahip olup olmadığınızı ve 8 bite kadar genişletmek istediğinizi düşünün. Yapılacak en basit şey sadece sola kaydırmak ve düşük üç biti sıfır bırakmak olacaktır. Sorun şu ki, saf beyaza kadar gitmiyor. Ulaşabileceğiniz en yüksek yoğunluk seviyesi 11111000 veya 248'dir. Yani 8 bitlik ekranın tam yoğunluk aralığını kullanmıyorsunuz.

Gerçekten, intensity8 = round(intensity5 * 255.0 / 31.0)[0, 31] aralığını [0, 255] olarak yeniden ölçeklendirmek gibi bir hesaplama yapmak istersiniz . Bununla birlikte, bunu herhangi bir kayan nokta matematiği veya bölünmesi olmadan başarmak için düzgün bir hile vardır: düşük üç biti yüksek üç bite eşit olarak ayarlayın. Yani, yoğunluğu 5 bit'ten 8 bit'e dönüştürmek için

intensity8 = (intensity5 << 3) | (intensity5 >> 2);

Daha sonra 11111'lik bir yoğunluk 11111111'e eşlenir (31 haritadan 255'e) ve ara sonuçlar da aklı başında bir şey yapar, örneğin 10000 -> 10000100 (16 -> 132).

Bu sayı kümesi tam olarak sahip olduğunuz şeydir. İlk örneğinizin kırmızı bileşenini aldığınızda:

132    10000100
123    01111011
115    01110011
107    01101011
 99    01100011
 90    01011010
 82    01010010
 74    01001010

Düşük üç bitin her zaman ilk üç bite nasıl eşit olduğuna dikkat edin. 9 farkı, hem bit 0 hem de bit 3 aynı anda çevrildiğinde ortaya çıkar.

Bu durumda 5 bit yoğunluk seviyelerinin neden kullanılacağından emin değilim; belki de bu, arcade makinesinin donanımının sınırıydı? 5 bit RGB değerinin 16 bitlik bir kelimeye iyi uyan 15 bit olması dikkat çekicidir. Her durumda, bu tek 8-8-8-9 modelini açıklar.


1
Piksel başına 16 bit 'Yüksek Renk' olarak adlandırıldı. (Bu benim hatırladığım her şey hakkında) en.wikipedia.org/wiki/High_color
römorkörler

1
Wikipedia yoluyla hızlı bir seyahatten sonra Sega Saturn ( en.wikipedia.org/wiki/Sega_Saturn#Video ) 15 bit renkli görüntü modunu yanı sıra GameBoy Advance (bahseder en.wikipedia.org/wiki/Game_Boy_Advance )
römorkörler

1
Harika! Şimdi hepsi anlam kazanıyor. Teşekkür ederim!
Archagon

Oyun 16 bit renge sahip olmalı ve sanatçılar muhtemelen bir RGBA 5551 renk şeması vererek şeffaflık pahasına oyunlarından daha fazla renk sıkmak istiyorlardı.
Archagon

0

Mod 13h veya 256 renk paleti solmasına bakmalısınız. O zamanlar, o kadar çok renge sahiptiniz ve yaptığınız şey, tüm paletle uğraştı, çünkü içinde olmayan yeni renkleri hesaplayamadınız.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.