ベーマガとチャレアベ本の修復

手持ちの古い雑誌や本がどんどん劣化していくので、修理してみました。

f:id:nicotakuya:20210420181724j:plain

破れたベーマガ(1986年)

▲たとえば、こちらは簡単な例。35年前のベーマガ

表紙が破れてますが、ノリで貼り直しました。

 

f:id:nicotakuya:20210420182447j:plain

バラバラになったページ

▲もっと激しく壊れた例。これは背の一部が剥がれたり、裏表紙が丸ごと取れてしまってます。

背の部分はノリで貼り付けました。アラビックヤマトだと、貼った部分が茶色になってしまうので良くないかもしれません。

裏表紙は丈夫に付ける必要があるので、木工用ボンドで貼りました。

 

f:id:nicotakuya:20210420182532j:plain

ページの破れ

▲続いて、裏表紙が破れた場合。

これは難しいですね。セロハンテープは劣化するので厳禁です。PP(ポリプロピレン)テープは見た目が良くないので、使いたくありません。

 

f:id:nicotakuya:20210421082253j:plain

カバーを被せた様子

▲そこで、透明ブックカバーをかぶせて対処しました。写真だとわかりにくいですが、フィルムをかぶせてます。

 

f:id:nicotakuya:20210420182544j:plain

透明ブックカバーB5サイズ

▲使ったカバーはこれです。 東急ハンズで352円。

 

f:id:nicotakuya:20210421230617j:plain

 粘着テープまみれの「チャレンジ!!パソコンAVGRPG(1986年)」

▲これは難物です。

3年前に中古で買ったチャレアベ本です。お値段、なんと4000円。

あちらこちらに粘着テープが貼られてます。

 

f:id:nicotakuya:20210421151309j:plain

本を開いただけで2つに分かれる

▲驚くのはその劣化ぶり。

本を開くと、こんな感じで2つに分かれてしまいます。本の「背」がつながっていなくて、粘着テープだけでどうにか形を保っている状態。

f:id:nicotakuya:20210423063925j:plain

変色したセロハンテープ

この本、「ザナドゥ」のマップが載っているページだけ劣化が激しいです。だいたい20ページに渡ってページが外れていて、閉じ部分にセロハンテープがびっしりと貼られてます。

このマップって、閉じ部分の根本まで印刷しているのが困りもの。それを無理して読もうとするので、結果として本を破壊してしまいます。

 

f:id:nicotakuya:20210421151722j:plain

鉛筆の書き込み

▲本の前の持ち主さんは熱心なザナドゥのプレイヤーだったみたいです。

あちこちに鉛筆の書き込みがありました。「G」とか「R」は敵の種類か?

これは消しゴムをかけると、印刷が消えちゃいそうなので、そのままにしておきます。

 

f:id:nicotakuya:20210421230145j:plain

ページの折れ

▲ページが豪快に折れてます。1ページずつ指で真っ直ぐにします。

 

f:id:nicotakuya:20210421151637j:plain

ドライヤーで温めながら、テープをはがす

▲セロハンテープが茶色に変色しているので、剝がして捨てます。

ただし、そのまま剥がそうとすると、ページが破れる可能性が非常に高い。そこで、ドライヤーで温めながらゆっくりと剥がします。指をヤケドしないように、剥がす瞬間はドライヤーを切らないといけないので、手間がかかります。

あと、セロハンテープは色が移ってしまって、剥がしても紙に茶色の痕が残ってしまいます。困りますが、どうにもなりません。

 

f:id:nicotakuya:20210422141612j:plain

セロハンテープとPPテープの二重攻撃

▲難所。セロハンテープの上に、幅4センチくらいの太いPPテープがガッチリと貼ってあります。PPテープは変色してないのですが、中のセロハンテープは茶色になっているので、すべて剥がします。根気を使います。

f:id:nicotakuya:20210421151515j:plain

表紙にも粘着テープがいっぱい

▲最大の難所。先ほどと同じく、2重に粘着テープが貼ってあります。背の部分はすでに細かく破れているので、テープを剥がそうとすると、さらに破れる可能性があります。これは修復不能では、、、?

 

f:id:nicotakuya:20210421230258j:plain

PPテープの引き剥がしに成功

▲粘着テープと格闘を続けること数日。

諦めかけていたのですが、根気よく剥がしていったら、やっと取れました。

背の部分がボロボロです。カラープリンタで同じようなものを印刷して取り換えるという方法もありますが、できるだけ現物のままでいきます。 

 

f:id:nicotakuya:20210422121118j:plain

剥がした粘着テープ

▲本から剥がした粘着テープです。かつおぶしじゃありません。

合計で50枚くらいテープが貼られていました。

、、、よくもまあ、中古ショップの人はこれを4000円で売ろうと思ったな!?

 

f:id:nicotakuya:20210422121312j:plain

背にボンドを塗る

▲普通紙を木工用ボンドで貼って、本の背にします。

バラバラだったページを合体させます。

ボンドが多すぎると、余計にくっ付いて悲惨なことになるので、薄く伸ばしておきます。

 

f:id:nicotakuya:20210422120804j:plain

表紙を接着

▲表紙を貼り合わせ。

 

f:id:nicotakuya:20210422120925j:plain

透明カバーをかぶせて完成

▲ボンドが乾いたら、透明ブックカバーを付けます。

 

f:id:nicotakuya:20210422120555j:plain

修復に成功

▲修理が終わりました。やっと本らしく扱うことができます。

裂けるのが怖いので、全力で本を開けません。

1.77インチ カラー液晶の表示テスト

f:id:nicotakuya:20210305012358j:plain
TFT液晶表示

とりあえず動きましたというレベルですが、マイコン(Arduino)を使って1.77インチ カラー液晶に表示してみました。
16bitモードで、RGB+グレースケールを32諧調グラデーション表示します。
使用した部品は以下のとおりです。
マイコン「Seeeduino XIAO」580円。
・1.77インチ カラーグラフィックTFT LCD 評価キット「AE-ATM0177B3A」1200円。
昔は32bitマイコンもカラー液晶も高くて手が出なかったのですが、今だと手軽に買えてしまいます。便利な世の中になりました。
Arduino IDEでSeeeduino XIAOを使う方法については、こちらのページで紹介されています。
https://wiki.seeedstudio.com/Seeeduino-XIAO/#software
接続図は以下の通りです。3.3Vで動かします。

f:id:nicotakuya:20210305131928p:plain
接続方法

プログラム(Arduino IDE用)は以下の通りです。「TFTCS」「TFTCD」「SPICLK」「SPIDAT」「TFTRST」のGPIO番号を書き換えれば、他のマイコンでも動くと思います。

// TFT test program by takuya matsubara

// 初期設定は Max MC Costa(sumotoy)さんの「TFT_ILI9163C」を参考にしています。
//https://github.com/sumotoy/TFT_ILI9163C

// Akizuki AE-ATM0177B3A
// 1.77inch ZETTLER COLOR TFT LCD(ILI9163V / 128x160 pixel)
//https://akizukidenshi.com/catalog/g/gK-14032/

// pin assign
//1: NC
//2: NC
//3: NC
//4: NC
//5: LED Anode
//6: NC
//7: NC
//8: GND
//9: VCC
//10: SDA
//11: SCK
//12: CD(H=Data/L=Command)
//13: RESET
//14: LED Cathode
//15: CS(L=active)

//Seeeduino XIAO - Arduino Microcontroller
//CPU:Arm Cortex M0+ 32bit 48 MHz(SAMD21)
//Flash:256 KB 
//SRAM:32 KB

// pin assign
//    [USB]
//D0         5V
//D1(RST)    GND
//D2(CS)     3V3
//D3(CD)     D10(MOSI)
//D4         D9(MISO)
//D5         D8(SCK)
//D6(TX)     D7(RX)

#define TFTCS     2   // chip select
#define TFTCD     3   // command/data
#define SPICLK    8   // clock
#define SPIDAT   10   // data
#define TFTRST    1   // reset

#define SOFTWARE_RESET            0x01
#define SLEEP_OUT                 0x11
#define PARTIAL_MODE_ON           0x12
#define NORMAL_DISPLAY_MODE_ON    0x13
#define DISPLAY_INVERSION_OFF     0x20
#define DISPLAY_INVERSION_ON      0x21
#define GAMMA_SET                 0x26
#define DISPLAY_OFF               0x28
#define DISPLAY_ON                0x29
#define COLUMN_ADDRESS_SET        0x2A
#define PAGE_ADDRESS_SET          0x2B
#define MEMORY_WRITE              0x2C
#define V_SCROLL_DEFINITION       0x33
#define MEMORY_ACCESS_CONTROL     0x36
#define V_SCROLL_START_ADDRESS    0x37
#define INTERFACE_PIXEL_FORMAT    0x3A
#define FRAME_RATE_CONTROL_1      0xB1
#define DISPLAY_INVERSION_CONTROL 0xB4
#define DISPLAY_FUCTION_SET       0xb6
#define POWER_CONTROL_1           0xC0
#define POWER_CONTROL_2           0xC1
#define VCOM_CONTROL_1            0xC5
#define VCOM_OFFSET_CONTROL       0xC7
#define POSITIVE_GAMMA            0xE0
#define NEGATIVE_GAMMA            0xE1
#define GAM_R_SEL                 0xF2

#define GRAMWIDTH        128  // width[pixel]
#define GRAMHEIGHT       160  // height[pixel]

#define SPIWAIT 5

void waitloop(long count){
  while(count--);
}

void spi_sendbyte(unsigned char data){
  unsigned char bitmask;
  waitloop(SPIWAIT);
  digitalWrite(TFTCS,LOW);
  digitalWrite(SPICLK, LOW);
  waitloop(SPIWAIT);
  bitmask = 0x80;
  while(bitmask){
    if(bitmask & data){
      digitalWrite(SPIDAT, HIGH);
    }else{
      digitalWrite(SPIDAT, LOW);
    }    
    waitloop(SPIWAIT);
    digitalWrite(SPICLK, HIGH);
    waitloop(SPIWAIT);
    digitalWrite(SPICLK, LOW);
    bitmask >>= 1;
  }
  waitloop(SPIWAIT);
  digitalWrite(TFTCS,HIGH);
  waitloop(SPIWAIT);
}

void tft_sendcmd(unsigned char data){
  delay(1);
  digitalWrite(TFTCD,LOW);
  spi_sendbyte(data);
  digitalWrite(TFTCD,HIGH);
}

void tft_send_data(unsigned char data){
  digitalWrite(TFTCD,HIGH);
  spi_sendbyte(data);
}

void tft_sendcmd_15byte(unsigned char cmd,unsigned char *data){
  int cnt;
  tft_sendcmd(cmd);
  cnt=15;
  while(cnt--){
    tft_send_data(*data++);
  }
}

void tft_sendcmd_byte(unsigned char cmd,unsigned char data){
  tft_sendcmd(cmd);
  tft_send_data(data);
}

void tft_sendcmd_word(unsigned char cmd,unsigned int data){
  tft_sendcmd(cmd);
  tft_send_data((unsigned char)(data >> 8));
  tft_send_data((unsigned char)(data & 0xff));
}

void tft_sendcmd_long(unsigned char cmd,unsigned long data){
  tft_sendcmd(cmd);
  tft_send_data((unsigned char)(data >> 24));
  tft_send_data((unsigned char)((data >> 16)& 0xff));
  tft_send_data((unsigned char)((data >> 8)& 0xff));
  tft_send_data((unsigned char)(data & 0xff));
}

// test pattern
void tft_display_test(void){
  int x,y;
  char mode;
  unsigned int r,g,b,color;
  tft_sendcmd(MEMORY_WRITE);
  delay(150);  
  color=0;
  for(y=0; y<160; y++){
    for(x=0; x<128; x++){
      mode = (y / 40);
      if(mode==0) color = ((y % 40)*0x1f/39);     //blue
      if(mode==1) color = ((y % 40)*0x1f/39)<<6;  //green
      if(mode==2) color = ((y % 40)*0x1f/39)<<11; //red
      if(mode==3){ //grayscale
        b=(y % 40)*0x1f/39;
        r=b;
        g=b;
        color = (r<<11)+(g<<6)+b; 
      }
      tft_send_data(color >> 8);
      tft_send_data(color & 0xff);
    }
  }
}

void setup(void) {
  pinMode(SPIDAT, OUTPUT);
  pinMode(SPICLK, OUTPUT);
  pinMode(TFTCD, OUTPUT);
  pinMode(TFTCS, OUTPUT);
  pinMode(TFTRST, OUTPUT);
  digitalWrite(SPIDAT, HIGH);
  digitalWrite(SPICLK, LOW);
  digitalWrite(TFTCD, HIGH);
  digitalWrite(TFTCS, HIGH);
  digitalWrite(TFTRST, HIGH);
  delay(500);
  tft_sendcmd(SOFTWARE_RESET);
  delay(500);
  tft_sendcmd(SLEEP_OUT);
  delay(5);
  tft_sendcmd_byte(INTERFACE_PIXEL_FORMAT, 0x05);  //16bit
  tft_sendcmd_byte(GAMMA_SET,0x04);
  tft_sendcmd_byte(GAM_R_SEL,0x01);
  tft_sendcmd(NORMAL_DISPLAY_MODE_ON);
  tft_sendcmd_word(DISPLAY_FUCTION_SET,0xff06);
  tft_sendcmd_word(FRAME_RATE_CONTROL_1,0x0802);
  tft_sendcmd_byte(DISPLAY_INVERSION_CONTROL,0x07);
  tft_sendcmd_word(POWER_CONTROL_1,0x0A02);
  tft_sendcmd_byte(POWER_CONTROL_2,0x02);
  tft_sendcmd_word(VCOM_CONTROL_1,0x5063);
  tft_sendcmd_byte(VCOM_OFFSET_CONTROL,0x00);
  tft_sendcmd_long(COLUMN_ADDRESS_SET,GRAMWIDTH-1); 
  tft_sendcmd_long(PAGE_ADDRESS_SET,GRAMHEIGHT-1); 
  tft_sendcmd(DISPLAY_ON);
}
 
void loop() {
  delay(500);  
  tft_display_test();
}

液晶の初期設定のパラメータはMax MC Costa(sumotoy)さんの「TFT_ILI9163C」を使わせて頂きました。ガンマの設定はよくわからないので削っています。

プログラムには間違いがある可能性があります。間違いを見つけた場合は直して使ってみてください。

M5StickCのキャプチャ実験

f:id:nicotakuya:20210226153653j:plain
M5StickCのキャプチャ

M5StickCのキャプチャできないか試してみました。まだ実験中です。
こちらの記事を参考にさせて頂きました。
raspberrypi.mongonta.com
これによると、ライブラリの「In_eSPI_Setup.h」というファイルを修正すると、「readPixel」が使えるようになるとのこと。readPixelは指定座標の画面のカラーコードを読み取るための関数です。
具体的な手順は以下のとおり。
「C:\Users\(ユーザー名)\Documents\Arduino\libraries\M5StickC\src\utility」フォルダの中にある「In_eSPI_Setup.h」をテキストエディタで開いて、次の2点を修正します。

f:id:nicotakuya:20210226151729p:plain
修正1

(修正1)「TFT_SDA_READ」の左側にある「//」を削除する。

f:id:nicotakuya:20210226151808p:plain
修正2

(修正2)「SPI_READ_FREQUENCY」の値を変更する。適切な値がわかりませんが「4000000」にしました。ビットレートが大きいと通信に失敗するようです。

↓が実験用のプログラムです。M5StickCに書き込むArduinoのスケッチです。Aボタン(M5ボタン)が押されたら、画面のデータをシリアルポートから出力します。

// capture
#include <M5StickC.h>

void capture(void){
  unsigned int color;
  int x,y;

  if(digitalRead(M5_BUTTON_HOME) == HIGH)return;
  while(digitalRead(M5_BUTTON_HOME) == LOW);

  for(y=0; y<80; y++){
    for(x=0; x<160; x++){
        color = M5.Lcd.readPixel(x,y);
        Serial.write((unsigned char)(color & 0xff));
        Serial.write((unsigned char)(color >> 8));
        Serial.flush();  // シリアル出力完了を待つ
    }  
  }  
}

void setup() {
  M5.begin();
  M5.Lcd.setRotation(3);
  M5.Lcd.setTextSize(3);
  M5.Lcd.setTextColor(RED);
  M5.Lcd.print("HELLO WORLD");
  M5.Lcd.setTextColor(BLUE);
  M5.Lcd.print("HELLO WORLD");
  M5.Lcd.setTextColor(GREEN);
  M5.Lcd.print("HELLO WORLD");
}

void loop() {
  capture();
}

そして、
↓がパソコン側の受信用のプログラムです。HSP3(Windows)で動きます。シリアルポートから受信した内容を画面に描画します。

//---------------------------------------------------------
//  for HSP 3   by takuya matsubara
// ・M5StickCのキャプチャを受信
//---------------------------------------------------------
#include "hspext.as"

#define LEDWIDTH  160	//width pixel
#define LEDHEIGHT 80	//height pixel
#define OFFSETX 0
#define OFFSETY 0
#define DOTSZ 3
#define BAUDRATE 115200

sdim livebuf,LEDWIDTH*LEDHEIGHT
screen 0,800,512,0,0,0
dispw = DOTSZ*LEDWIDTH
disph = DOTSZ*LEDHEIGHT
flag_comm =0
objsize 70,25
pos 0,400
button gosub "Open",*connect
pos 70*3+10,400
print "COMM"
pos 70*3+50,400
comnum=0
combox comnum,150,"com\ncom1\ncom2\ncom3\ncom4\ncom5\ncom6\ncom7\ncom8\ncom9\ncom10\n"
pos 70*6,400
button gosub "Save BMP",*savegrp

x1=OFFSETX
y1=OFFSETY
ptr=0
colordata=0
repeat
	if(flag_comm==0){
		wait 1
	}else{
		//recv
		repeat
			comgetc btn	//recv 1byte
			if(stat != 0){
				if(ptr==0):colordata = btn
				if(ptr==1):colordata = (btn<<8)+colordata
				ptr = (ptr+1) \ 2
				if(ptr==0){
					red  = (colordata >> (5+6)) & $1f	//32諧調
					green= (colordata >> 5) & $3f	//64諧調
					blue = colordata & $1f	//32諧調
					x2 = x1+DOTSZ-1
					y2 = y1+DOTSZ-1
					red = red*255/$1f
					green = green*255/$3f
					blue = blue*255/$1f

					//暗いので2倍にする(原因不明)
					red*=2
					green*=2
					blue*=2
					if red>255:red=255
					if green>255:green=255
					if blue>255:blue=255
					color red,green,blue
					boxf x1,y1,x2,y2
					
					x1 += DOTSZ
					if(x1 >= ((DOTSZ*LEDWIDTH)+OFFSETX)){
						x1=OFFSETX
						y1+=DOTSZ
						if(y1 >= ((DOTSZ*LEDHEIGHT)+OFFSETY)){
							y1 = OFFSETY
						}
					}
				}
			}else{
				redraw 1
				wait 1	//no data
				redraw 0
			}
		loop
	}
loop	
end

//-------------
*savegrp
gosub *connect_close
dialog "bmp",17,"BMPファイル"
if stat==0:return
filename=refstr
screen 1,LEDWIDTH*DOTSZ,LEDHEIGHT*DOTSZ
gsel 1,1
pos 0,0
gcopy 0,0,0,LEDWIDTH*DOTSZ,LEDHEIGHT*DOTSZ
bmpsave filename
gsel 1,-1
gsel 0,0
return
	
*connect_open
	if(flag_comm = 0){
		comopen comnum,"baud="+str(BAUDRATE)+" parity=N data=8 stop=1"
		if stat : dialog "COM"+comnum+"は使えません" : end
		flag_comm=1

		repeat
			comgetc btn	//recv 1byte
			if(stat == 0):break
		loop
		ptr=0
		x1=OFFSETX
		y1=OFFSETY
	}
	return

*connect_close
	if(flag_comm = 1){
		comclose
		flag_comm=0
	}
	return

*connect
	if(flag_comm =0){
		gosub *connect_open
		title "OPEN COMM"+str(comnum)
		wait 150	//必須
	}else{
		gosub *connect_close
		title "CLOSE COMM"
	}
	return

M5StickCをパソコンのUSBポートに接続してある状態で上記のプログラムを実行します。

f:id:nicotakuya:20210226151149p:plain
実行結果

画面の「OPEN」ボタンを押してシリアルポートの回線を開きます。M5StickCのAボタン(M5ボタン)を押すと、画像データが転送されます。通信速度は115200bpsです。
未解決の問題ですが、受信したカラーコードはすべて、想定の半分になってしまいます。ここままだと画像が暗くなってしまうので、受信した直後に2倍にして描画しています。各色ずつ1bit足りないので、16bitカラーではなく、13bitカラーになっていると思います。

ファミコン用マルチタップの自作version2

f:id:nicotakuya:20210225183004j:plain

マルチタップversion1

上の写真が以前作ったファミコン用マルチタップです。今のところ、くにおくんの大運動会で使うしか意味のない周辺機器です。

作ったのは良いんですが、ファミコン用パッドが入手できなかったので、このようにスーファミ用パッドを変換して接続してました。これがちょっと無駄に感じます。

 

f:id:nicotakuya:20210225183133j:plain

マルチタップversion2(動作未確認)

そこで、新バージョンでは、基板に最初からスーファミのコネクタを取り付けてみました。ただ、このコネクタを付けると、今度はdsub 15pinが付けられなくなります。2種類組み立てたらいいんじゃないでしょうか。もしくは裏側にハンダ付けするか。

 

f:id:nicotakuya:20200717031158j:plain

スーファミ用コネクタ

スーファミ用のコネクタです。基板取り付け用。

 

f:id:nicotakuya:20210225183349j:plain

14x4cm基板

基板サイズは14x4にして、秋月製のユニバーサル基板を底に付けられるようにしました。

以下のページでCADデータを公開中です。動作未確認なので、ご注意ください。

sites.google.com

洞窟物語

f:id:nicotakuya:20210221145122p:plain

メガドラ洞窟物語?!

AliExpressでメガドライブ版の「洞窟物語(Cave Story)」が売っていました。「洞窟物語」というのは、2004年12月から公開されているフリーのアクションゲームです。有料版もあります。インディーズのゲームって、なぜかメトロイドヴァニアに傾倒しているのですが、その源流ですね。

このメガドラ版は非合法なソフトなわけですが、検索したらGitHubにソースがありました。

 

f:id:nicotakuya:20210221131910p:plain

メガドライブ洞窟物語(Cave Strory)

GitHub内のライセンス表記より。

上から2番目にある「NXEngine」とは洞窟物語のクローンです。ゲームエンジンではありません。これはオープンソースで開発しているおかげで、いろいろな機種に移植されてます。作ったのは本家のPixelさんではなく、Caitlin Shawさんという人のようです。

 

気になるのは上から三番目。「グラフィック、ストーリー、キャラクター」のライセンスが書かれていません(Studio Pixelになってます)

改変はOKなのか?

再配布はOKなのか?

という点が不明のままです。これは大丈夫なのか、、、?

 

そして、去年、わりと衝撃的だったニュースがこちら↓。

automaton-media.com

 

恥ずかしながら、自分はこれ見るまで「洞窟物語は本家がオープンソース」だと誤解してました。まさか第三者勝手にオープンソースにしてただけだったとは。

今回、申し立てしたのがWiiウェア/3DS/Switch版の洞窟物語を作っているNicalis社。問題の「Cave Story Engine 2」は改造Switch(SXOS)で動いていたので、営業妨害に当たりますね。改造Switchを持ってる時点でダメですが。あと、作った側が「逆コンパイルした(リバースエンジニアリングした)」と正直に告白していたのもアウトな気がします。

Cave Story Engine 「2」ってことは、「1」はNXEngineのことでしょうか? NXEngineは、開発手法が不明で、どこまで合法なのかわからないです。目コピーとは思えないほど出来が良いので、こちらもリバースエンジニアリングしてる可能性が高いです。となると、これはオリジナルの改変ですね。あと、グラフィックの素材は本物を流用しています。ここでも洞窟物語の再配布・改変がアリか/ナシか」という問題に突き当たります。洞窟物語のフリー版は今でもStudio PixelVECTORからダウンロードできますが、ライセンスについては何も書いてありません。先のGitHubのライセンスが空白だったのは、これが理由です。

もし、Nicalis社がNXEngineに申し立てをした場合、10年ほど築き上げた洞窟物語のクローンがすべて崩壊してしまいます。事態が大きくなりすぎです。

、、、これ以上の話は自分の手に余るので、詳しい人にお任せしたいです。

 

あと、「洞窟物語」で検索して、出てきたページがこちら。

http://909.xii.jp/blog/2011/11/03/

驚いたのは、まず作者のPixelさんが学生時代に作ったゲームがクオリティ高すぎること。そして、1999年時点で洞窟物語アルファ版があったこと。開発におよそ5年費やしたこと。2~3年作ってから、それを捨てて、丸ごと作り直したこと。病気のこと。「洞窟物語」はフリーゲームとは思えないくらい作り込みが尋常ではありませんが、その理由を推測することができます。

作り直しによってボツになったゲーム(https://www.youtube.com/watch?v=PRJcxyVgoug)って、動きが良いし、どこが悪いのかわからないのですが、Pixelさんからすると、全ボツに値するようです。それだけ目標が高かったということですね。公開までのラストの1年間はお仲間の意見を聞いて、バランス調整と改良をしてますが、こういう謙虚で実直な姿勢を保てるところが凄い。普通のアマチュアならアッという間に挫折します。

ゲームを作ってて、それが面白くないという事態に直面した場合、どうにかして面白くしないといけないのですが、ここにうまい回答は存在しません。虎の巻みたいなものがあったら読みたいですが。大体は面白くできないまま終わります。アマチュアなら、自分一人が喜べばいいだけですが、プロなら他人が喜ばないと意味がありません。Pixelさんの場合は、最初からプロ意識が高くて、どうにかして面白くする方法を探り当てたということでしょうか。実際、Pixelさんはプロに転向して、「ケロブラスター」をリリースしています。

f:id:nicotakuya:20210222004217j:plain

「ケロブラスター」

ケロブラスターは驚くほど安いので買ってみました。