Crossfire Client, Branch
R11627
|
00001 const char *rcsid_x11_sound_c = 00002 "$Id: sound.c 9215 2008-06-02 18:31:04Z anmaster $"; 00003 /* 00004 Crossfire client, a client program for the crossfire program. 00005 00006 Copyright (C) 2001 Mark Wedel & Crossfire Development Team 00007 00008 This program is free software; you can redistribute it and/or modify 00009 it under the terms of the GNU General Public License as published by 00010 the Free Software Foundation; either version 2 of the License, or 00011 (at your option) any later version. 00012 00013 This program is distributed in the hope that it will be useful, 00014 but WITHOUT ANY WARRANTY; without even the implied warranty of 00015 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00016 GNU General Public License for more details. 00017 00018 You should have received a copy of the GNU General Public License 00019 along with this program; if not, write to the Free Software 00020 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 00021 00022 The author can be reached via e-mail to crossfire-devel@real-time.com 00023 */ 00024 00031 #include <config.h> 00032 #include <stdio.h> 00033 #include <stdlib.h> 00034 #include <ctype.h> 00035 #include <signal.h> 00036 #include <client-types.h> 00037 #include "client.h" 00038 00039 00040 int nosound=0; 00041 00042 /* Got a pipe signal. As of now, only thing we are piped to is the 00043 * sound client. 00044 */ 00045 void signal_pipe(int i) { 00046 /* do nothing, but perhaps do something more in the future */ 00047 } 00048 00049 FILE *sound_pipe; 00050 ChildProcess* sound_process; 00051 00052 00053 /* init_sounds open the audio device, and reads any configuration files 00054 * that need to be. It returns 0 on success. On failure, the calling 00055 * function will likely disable sound support/requests from the server. 00056 */ 00057 00058 int init_sounds(void) 00059 { 00060 /* Easy trick - global nosound is set in the arg processing - if set, 00061 * just return -1 - this way, the calling function only needs to check 00062 * the value of init_sounds, and not worry about checking nosound. 00063 */ 00064 if (!want_config[CONFIG_SOUND]) return -1; 00065 00066 /*if (sound_process) //kill*/ 00067 00068 sound_process=raiseChild(BINDIR "/cfsndserv",CHILD_STDIN|CHILD_STDOUT|CHILD_STDERR); 00069 logChildPipe(sound_process, LOG_INFO, CHILD_STDOUT|CHILD_STDERR); 00070 sound_pipe=fdopen(sound_process->tube[0],"w"); 00071 signal(SIGPIPE, signal_pipe);/*perhaps throwing this out :\*/ 00072 return 0; 00073 } 00074 00075 00076 00077 /* Plays sound 'soundnum'. soundtype is 0 for normal sounds, 1 for 00078 * spell_sounds. This might get extended in the future. x,y are offset 00079 * (assumed from player) to play sound. This information is used to 00080 * determine value and left vs right speaker balance. 00081 * 00082 * This procedure seems to be very slow - much slower than I would 00083 * expect. Might need to run this is a thread or fork off. 00084 */ 00085 00086 static void play_sound(int soundnum, int soundtype, int x, int y) 00087 { 00088 if (nosound) return; 00089 00090 if (fprintf(sound_pipe,"%4x %4x %4x %4x\n",soundnum,soundtype,x,y)<=0) { 00091 nosound=1; 00092 fclose(sound_pipe); 00093 return; 00094 } 00095 if (fflush(sound_pipe)!=0) { 00096 nosound=1; 00097 fclose(sound_pipe); 00098 return; 00099 } 00100 } 00101 00102 00103 void SoundCmd(unsigned char *data, int len) 00104 { 00105 int x, y, num, type; 00106 00107 if (len!=5) { 00108 fprintf(stderr,"Got invalid length on sound command: %d\n", len); 00109 return; 00110 } 00111 x = data[0]; 00112 y = data[1]; 00113 num = GetShort_String(data+2); 00114 type = data[4]; 00115 00116 #if 0 00117 fprintf(stderr,"Playing sound %d (type %d), offset %d, %x\n", 00118 num, type, x ,y); 00119 #endif 00120 play_sound(num, type, x, y); 00121 } 00122 00123 void Sound2Cmd(unsigned char *data, int len) 00124 { 00125 uint8 x, y, dir, volume, type, len_action; 00126 char* action = NULL; 00127 uint8 len_name; 00128 char* name = NULL; 00129 /* sound2 <x><y><dir><volume><type><len of action>action<len of name>name */ 00130 /* b b b b b b str b str*/ 00131 if (len<8) { 00132 fprintf(stderr, "Got too short length on sound2 command: %d\n", len); 00133 return; 00134 } 00135 x = data[0]; 00136 y = data[1]; 00137 dir = data[2]; 00138 volume = data[3]; 00139 type = data[4]; 00140 len_action = data[5]; 00141 /* Prevent invald index. */ 00142 if (len_action >= (len-8)) { 00143 fprintf(stderr, "Bad length of \"len of action\" in sound2 command: %d\n", len); 00144 return; 00145 } 00146 if (len_action != 0) { 00147 action = (char*)data+6; 00148 data[6+len_action]='\0'; 00149 } 00150 /* Lets make it readable, compiler will optimize the addition order anyway*/ 00151 len_name = data[6+len_action+1]; 00152 if (len_name >= (len-8-len_action)) { 00153 fprintf(stderr, "Bad length of \"len of name\" in sound2 command: %d\n", len); 00154 return; 00155 } 00156 if (len_name != 0) { 00157 name = (char*)data+6+len_action+1; 00158 data[6+len_action+1+len_name]='\0'; 00159 } 00160 00161 fprintf(stderr, "Playing sound2 x=%hhd y=%hhd dir=%hhd volume=%hhd type=%hhd\n", 00162 x, y, dir, volume, type); 00163 fprintf(stderr, " len_action=%hhd action=%s\n", len_action, action); 00164 fprintf(stderr, " len_name=%hhd name=%s\n", len_name, name); 00165 fprintf(stderr, "Please impement sound2!"); 00166 /* TODO: Play sound here. Can't implement/test as server never actually 00167 * sends this yet it seems. As this code is mostly duplicated between the 00168 * different clients, make sure to update the other ones too. 00169 */ 00170 } 00171 00172 00173 void MusicCmd(const char *data, int len) { 00174 if (!strncmp(data, "NONE", len)) { 00175 /* TODO stop music */ 00176 } else { 00177 fprintf(stderr, "gtk::MusicCmd", "music command: %s (Implement me!)\n", data); 00178 /* TODO: Play music. Can't impmement/test as server doesn't send this 00179 * version of the command yet it seems. 00180 */ 00181 } 00182 }