/*---------------------------------------------------------------------------* Project: NintendoWare File: snd_AnimSoundFile.h Copyright (C)2009-2011 Nintendo/HAL Laboratory, Inc. All rights reserved. These coded instructions, statements, and computer programs contain proprietary information of Nintendo and/or its licensed developers and are protected by national and international copyright laws. They may not be disclosed to third parties or copied or duplicated in any form, in whole or in part, without the prior written consent of Nintendo. The content herein is highly confidential and should be handled accordingly. $Revision: $ *---------------------------------------------------------------------------*/ #ifndef NW_SND_ANIM_SOUND_FILE_H_ #define NW_SND_ANIM_SOUND_FILE_H_ #include #include #include namespace nw { namespace snd { class SoundArchive; namespace internal { /* アニメーションサウンドファイル (.bcasd) の構造 bcasd | +-- FileHeader +-- DataBlock | +-- BinaryBlockHeader +-- DataBlockBody | +-- u32 frameSize +-- Reference toAnimEventTable | +--- ( &DataBlockBody + toAnimEventTable.offset ) --+ | +------------------------------------------------------------------+ | +--> AnimEventTable | +-- u32 count +-- AnimEvent item[count] | +-- FrameInfo | | | +-- s32 startFrame | +-- s32 endFrame | +-- u8 frameFlag | +-- s8 loopOffset | +-- u8 loopInterval | +-- u8 reserved | +-- Reference toEventInfo | +-- ( &item[...] + toEventInfo.offset ) --+ | +------------------------------------------------------------+ | +--> EventInfo | +-- u32 optionFlag +-- u32 placeForSoundId +-- Reference toSoundLabel | | | +-- ( &EventInfo + toSoundLabel.offset ) --+ | | | +---------------------------------------------+ | | | +--> const char* soundLabel | +-- u8 volume +-- u8 playDirection +-- u8 sequenceVariableNo +-- u8 reserved1 +-- f32 pitch +-- u32 reserved2 +-- u32 userParam */ struct AnimSoundFile { // 前方宣言 struct DataBlock; struct AnimEvent; struct AnimEventFrameInfo; struct FileHeader : public Util::SoundFileHeader { const DataBlock* GetDataBlock() const; }; // フレーム情報。開始・終了位置やループについての情報を保持。 struct FrameInfo { // フレーム処理のオプションフラグ enum FrameFlag { FRAME_FLAG_TRIGGER_EVENT = 0x01, // トリガタイプのイベント FRAME_FLAG_END_FRAME_INF = 0x02, // 終了フレームが無限大 FRAME_FLAG_START_FRAME_INF = 0x04 // 開始フレームが負無限大 }; // データ nw::ut::ResS32 startFrame; // イベント開始フレーム nw::ut::ResS32 endFrame; // イベント終了フレーム (* の場合は 0xffffffff) nw::ut::ResU8 frameFlag; // 参照: AnimSoundImpl::FrameFlag nw::ut::ResS8 loopOffset; // 再生ループ数 nw::ut::ResU8 loopInterval; // loopCount 以降で再生するループ間隔 u8 reserved; }; // イベント情報。どのサウンドを、どのようなピッチで鳴らすかなどの情報を保持。 struct EventInfo { // オプションフラグタイプ enum OptionFlag { OPTION_FLAG_IS_NOT_STOP_SOUND_WHEN_ANIMATION_FINISH = (1<<0), OPTION_FLAG_IS_ENABLE_SEQUENCE_VARIABLE = (1<<1) }; // 再生方向 enum PlayDirection { PLAY_DIRECTION_BOTH = 0, // 両方向 PLAY_DIRECTION_FORWARD = 1, // 順方向 PLAY_DIRECTION_BACKWARD = 2 // 逆方向 }; // データ nw::ut::ResU32 optionFlag; // 参照: OptionFlag nw::ut::ResU32 placeForSoundId; // バイナリには SoundArchive::INVALID_ID // (0xffffffff) が書かれるが、WriteSoundId にて // 有効な値が書かれる。プレースホルダ。 Util::Reference toSoundLabel; nw::ut::ResU8 volume; nw::ut::ResU8 playDirection; // 参照: PlayDirection nw::ut::ResU8 sequenceVariableNo; // 0-15:ローカル変数、16-31:グローバル変数 u8 reserved1; nw::ut::ResF32 pitch; nw::ut::ResU32 reserved2; nw::ut::ResU32 userParam; // アクセサ const char* GetSoundLabel() const { NW_ASSERT( toSoundLabel.typeId == nw::snd::internal::ElementType_General_String ); return reinterpret_cast( ut::AddOffsetToPtr( this, toSoundLabel.offset ) ); } bool IsNotStopSoundWhenAnimationFinish() const { if ( optionFlag & OPTION_FLAG_IS_NOT_STOP_SOUND_WHEN_ANIMATION_FINISH ) { return true; } else { return false; } } bool GetSequenceVariable( u8* out ) const { if ( optionFlag & OPTION_FLAG_IS_ENABLE_SEQUENCE_VARIABLE ) { *out = sequenceVariableNo; return true; } else { return false; } } }; // フレーム情報と、イベント情報 (への参照) をまとめたコンテナ struct AnimEvent { FrameInfo frameInfo; // TODO: 将来的には Reference にしておいたほうが無難そう Util::Reference toEventInfo; const EventInfo* GetEventInfo() const { // シグニチャチェック NW_ASSERT( toEventInfo.typeId == nw::snd::internal::ElementType_AnimSoundFile_EventInfo ); return reinterpret_cast( ut::AddOffsetToPtr( this, toEventInfo.offset ) ); } }; typedef Util::Table AnimEventTable; // DATA ブロックのボディ (ブロックヘッダーを抜いた部分) struct DataBlockBody { nw::ut::ResU32 frameSize; // 総フレーム数 Util::Reference toAnimEventTable; // AnimEventTable へのオフセット const AnimEventTable* GetAnimEventTable() const { NW_ASSERT( toAnimEventTable.typeId == nw::snd::internal::ElementType_Table_EmbeddingTable ); return reinterpret_cast( ut::AddOffsetToPtr( this, toAnimEventTable.offset ) ); } }; struct DataBlock { ut::BinaryBlockHeader header; DataBlockBody body; }; }; // void WriteSoundId( void* animSoundData, const SoundArchive& arc ); } // namespace nw::snd::internal } // namespace nw::snd } // namespace nw #endif /* NW_SND_ANIM_SOUND_FILE_H_ */