1 /*
2  * OpenClonk, http://www.openclonk.org
3  *
4  * Copyright (c) 1998-2000, Matthes Bender
5  * Copyright (c) 2001-2009, RedWolf Design GmbH, http://www.clonk.de/
6  * Copyright (c) 2009-2016, The OpenClonk Team and contributors
7  *
8  * Distributed under the terms of the ISC license; see accompanying file
9  * "COPYING" for details.
10  *
11  * "Clonk" is a registered trademark of Matthes Bender, used with permission.
12  * See accompanying file "TRADEMARK" for details.
13  *
14  * To redistribute this file separately, substitute the full license texts
15  * for the above references.
16  */
17 
18 /* Helper classes for individual sounds and effects in sound system. */
19 
20 #include "platform/C4SoundSystem.h"
21 
22 class C4Object;
23 class C4SoundModifier;
24 
25 class C4SoundEffect
26 {
27 	friend class C4SoundInstance;
28 public:
29 	C4SoundEffect();
30 	~C4SoundEffect();
31 public:
32 	char Name[C4MaxSoundName+1];
33 	int32_t Instances{0};
34 	int32_t SampleRate, Length;
35 	C4SoundHandle pSample{0};
36 	C4SoundInstance *FirstInst{nullptr};
37 	C4SoundEffect *Next{nullptr};
38 public:
39 	void Clear();
40 	bool Load(const char *szFileName, C4Group &hGroup, const char *namespace_prefix);
41 	bool Load(BYTE *pData, size_t iDataLen, bool fRaw=false); // load directly from memory
42 	void Execute();
43 	C4SoundInstance *New(bool fLoop = false, int32_t iVolume = 100, C4Object *pObj = nullptr, int32_t iCustomFalloffDistance = 0, int32_t iPitch = 0, C4SoundModifier *modifier = nullptr);
44 	C4SoundInstance *GetInstance(C4Object *pObj);
45 	void ClearPointers(C4Object *pObj);
46 	int32_t GetStartedInstanceCount(int32_t iX, int32_t iY, int32_t iRad); // local
47 	int32_t GetStartedInstanceCount(); // global
48 
GetFullName()49 	const char *GetFullName() const { return Name; }; // return full name including the path prefix
50 protected:
51 	void AddInst(C4SoundInstance *pInst);
52 	void RemoveInst(C4SoundInstance *pInst);
53 };
54 
55 class C4SoundInstance
56 {
57 	friend class C4SoundEffect;
58 	friend class C4SoundSystem;
59 	friend class C4SoundModifier;
60 protected:
61 	C4SoundInstance();
62 public:
63 	~C4SoundInstance();
64 protected:
65 	C4SoundEffect *pEffect{nullptr};
66 	int32_t iVolume{0}, iPan{0}, iPitch{0}, iChannel{-1};
67 	bool pitch_dirty{false};
68 	C4TimeMilliseconds tStarted;
69 	int32_t iNearInstanceMax;
70 	bool fLooping;
71 	C4Object *pObj;
72 	int32_t iFalloffDistance;
73 	C4SoundModifier *modifier{nullptr};
74 	bool has_local_modifier{false};
75 	C4SoundInstance *pNext{nullptr};
76 
77 	// NO_OWNER or a player number signifying which player owns the viewport in which the sound is heard (best)
78 	// Note that this does NOT correspond to the player number given in the Sound() script function
79 	// (i.e. sounds played only for one player). For example, a global GUI sound would have player==NO_OWNER even if
80 	// it is played for a specific player only.
81 	int32_t player;
82 public:
getObj()83 	C4Object *getObj() const { return pObj; }
isStarted()84 	bool isStarted() const { return iChannel != -1; }
85 	void Clear();
86 	bool Create(C4SoundEffect *pEffect, bool fLoop = false, int32_t iVolume = 100, C4Object *pObj = nullptr, int32_t iNearInstanceMax = 0, int32_t iFalloffDistance = 0, int32_t inPitch = 0, C4SoundModifier *modifier = nullptr);
87 	bool CheckStart();
88 	bool Start();
89 	bool Stop();
90 	bool Playing();
91 	void Execute();
SetVolume(int32_t inVolume)92 	void SetVolume(int32_t inVolume) { iVolume = inVolume; }
SetPan(int32_t inPan)93 	void SetPan(int32_t inPan) { iPan = inPan; }
94 	void SetPitch(int32_t inPitch);
95 	void SetVolumeByPos(int32_t x, int32_t y, int32_t relative_volume = 100);
SetObj(C4Object * pnObj)96 	void SetObj(C4Object *pnObj) { pObj = pnObj; }
97 	void ClearPointers(C4Object *pObj);
98 	bool Inside(int32_t iX, int32_t iY, int32_t iRad);
GetModifier()99 	C4SoundModifier *GetModifier() const { return modifier; }
100 	void SetModifier(C4SoundModifier *new_modifier, bool is_global);
101 	void SetPlayer(int32_t new_player);
102 };
103 
104