秋葉原の“昔ながらの”部品屋さんが集まる「秋葉原ラジオストアー」が64年の歴史に幕を閉じ、2013年11月30日で閉館すると発表されました。「秋葉原ラジオストアー」は、その名前までは認識していなくとも「JR秋葉原駅から中央通りに出ようとすると見かける、ガード下のごちゃっとした素人お断り風の路地」といえばわかりますでしょうか。あの一角はいくつかの建物?の集合体なのですが、そのうちのひとつが「秋葉原ラジオストアー」です。秋葉原はラジオ(電子部品)の街→電気製品の街→PCの街→萌えの街、というような変遷を経ていますが、この「電子部品の街」の頃から全くその景色が変わっていない、ザ・秋葉原という雰囲気を残す一角といえるでしょう。
その「秋葉原ラジオストアー」が閉館する!?と聞き、昔からの秋葉原ユーザとしてはいてもたってもいられずRICOH THETAを持って、あの雰囲気を記録するために「勝手ストリートビュー」を撮影してまいりました。衝動的に、勝手に撮ってしまいましたごめんなさい!
上記地図の青丸が撮影地点です。順に地図右側から、画像をクリックするとパノラマに飛びます
地図上のお店が赤く示されているところが「秋葉原ラジオストアー」です。通路をはさんで反対側は「ラジオセンター」という別の建物で、こちらは今回閉館のアナウンスはありません。このあたり、ラジオストアーが閉館したらどういう景色になるんでしょうか…。
今回の撮影はRICOH THETAを頭上にかかげ、自作スクリプトで5秒に一回リモートシャッターで自動的にシャッターを切り続けるようにセットしそのまま通路を歩いて撮影しました。通路の端から端まで1分くらいでしょうか。THETAの機動力の高さが活かせたかなと思います。
参考までに、THETAでリモートシャッターを切るスクリプト(Perl)を以下に示します。AndroidではSL4A+Perl for Androidの組み合わせで端末上で実行可能です。本スクリプトはシャッターを1回切るだけですが、PTP_OC_InitiateCaptureの部分を繰り返すことで複数回シャッターを繰り返させることが可能です。
THETAはWiFi経由ではPTP-IPで通信しているようで、制御はこちらのドキュメントなどを参考にしました。
※このスクリプトはその後バージョンアップしています。詳細はこちらのページをごらんください
#!/usr/bin/perl # ------------------------------------------------------- # RICOH THETA Remote shutter # ------------------------------------------------------- use IO::Socket; #use Encode; # ----- TARGET THETA my $Addr = "192.168.1.1"; my $Port = 15740; # ----- My profile my $Name = "THETA_Shutter"; my $GUID = "8a7ab04f-ebda-4f33-8649-8bf8c1cdc838"; my ($command_sock, $event_sock, $result, $session_id, $transaction_id); # Init_Command $command_sock = &PTPIP_Open_Connection; &PTPIP_Init_Command_Request($command_sock); ($result, $session_id) = &PTPIP_Wait_Init_Command_Ack($command_sock); if ($result == 0) { die "No Init_Command_Ack"; } # Init_Event $event_sock = &PTPIP_Open_Connection; &PTPIP_Init_Event_Request($event_sock,$session_id); ($result) = &PTPIP_Wait_Event_Request_Ack($event_sock); if ($result == 0) { die "No Init_Event_Ack"; } $transaction_id = 0; # PTP_OC_OpenSession &PTPIP_Cmd_Request($command_sock, $transaction_id++, 0x1002, $session_id ); ($result) = &PTPIP_Wait_Cmd_Response($command_sock); if ($result == 0) { die "No Cmd_Response"; } # PTP_OC_InitiateCapture &PTPIP_Cmd_Request($command_sock, $transaction_id++, 0x100E, 0, 0 ); ($result) = &PTPIP_Wait_Cmd_Response($command_sock); if ($result == 0) { die "No Cmd_Response"; } &PTPIP_Close_Connection($event_sock); &PTPIP_Close_Connection($command_sock); exit; # ------------------------------------------------------- # Init_Command # ------------------------------------------------------- sub PTPIP_Init_Command_Request { my $sock = shift; my $payload = ""; $payload .= pack("H8H4H4H4H12",split('-',$GUID)); # GUID $payload .= Encode_UTF16LE($Name."\x00"); $payload .= pack("V",1); print $sock &PTPIP_pack_command( 1, $payload); } sub PTPIP_Wait_Init_Command_Ack { my $sock = shift; my ($result,$session_id,$target_guid,$target_name,$unknown1); my @error_response = (0,0); my ($cmd,$payload) = &PTPIP_Recv_Response($sock); if ($cmd != 2) { @error_response; exit; } $session_id = unpack("V",$payload); $payload = substr($payload,4); my (@guid) = unpack("H8H4H4H4H12",$payload); $target_guid = join('-',@guid); $payload = substr($payload,16); $target_name = Decode_UTF16LE(substr($payload,0,-4)); $payload = substr($payload,-4); $unknown1 = unpack("V",$payload); print "Target GUID :".$target_guid."\n"; print "Target Name :".$target_name."\n"; (1, $session_id); } # ------------------------------------------------------- # Init_Event # ------------------------------------------------------- sub PTPIP_Init_Event_Request { my $sock = shift; my $session_id = shift; my $payload = ""; $payload .= pack("V",$session_id); print $sock &PTPIP_pack_command( 3, $payload); } sub PTPIP_Wait_Event_Request_Ack { my $sock = shift; my @error_response = (0); my ($cmd,$payload) = &PTPIP_Recv_Response($sock); if ($cmd != 4) { @error_response; exit; } 1; } # ------------------------------------------------------- # Cmd_Request # ------------------------------------------------------- sub PTPIP_Cmd_Request { my $sock = shift; my $transaction_id = shift; my $cmd = shift; my @args = @_; my $payload = ""; $payload .= pack("V",1); $payload .= pack("v",$cmd); $payload .= pack("V",$transaction_id); $payload .= pack("V*",@args); print $sock &PTPIP_pack_command( 6, $payload); } sub PTPIP_Wait_Cmd_Response { my $sock = shift; my @error_response = (0); my ($cmd,$payload) = &PTPIP_Recv_Response($sock); # if ($cmd != 4) { @error_response; exit; } 1; } # ------------------------------------------------------- # PTPIP utils # ------------------------------------------------------- sub PTPIP_Open_Connection { my $sock = new IO::Socket::INET(PeerAddr=>$Addr,PeerPort=>$Port,Proto=>'tcp',TimeOut=>2); die "IO::Socket : $!" unless $sock; $sock; } sub PTPIP_Close_Connection { my $sock = shift; close($sock); } sub PTPIP_pack_command { my $cmd = shift; my $payload = shift; pack("VV",(length($payload)+8),$cmd).$payload; } sub PTPIP_Recv_Response { my $sock = shift; my ($buf,$len,$command_type,$packet_len); my @error_response = (0,''); # packet length $len = read($sock,$buf,4); if ($len != 4) { @error_response; exit; } $packet_len = unpack("V",$buf); if ($packet_len > 1024) { @error_response; exit; } if ($packet_len < 8 ) { @error_response; exit; } # command $len = read($sock,$buf,4); if ($len != 4) { @error_response; exit; } $command_type = unpack("V",$buf); # payload $len = read($sock,$buf,$packet_len-8); if ($len != ($packet_len-8)) { @error_response; exit; } ($command_type,$buf); } sub Encode_UTF16LE { my $str = shift; # encode('UTF16LE', $str); pack("v*",unpack("c*",$str)); } sub Decode_UTF16LE { my $str = shift; # decode('UTF16LE', $str) pack("c*",unpack("v*",$str)); }当初の目的だった「リモートシャッター」が動いたからもういいやー、とコマンドのレスポンスパース部を途中でほったらかしてありますがw、PTPIP_Wait_Cmd_Response の部分をもうちょっとちゃんと作って長いペイロードも受け取れるようになるといろいろとできる制御が広がるはず。そのあたりはまた後日、ということで。 この「勝手ストリートビュー」を作れる360度パノラマカメラ、RICOH THETAについては に詳しくレビューしてありますので、よろしければこちらもどうぞ。