Crossfire Server, Trunk  R213250
party.c
Go to the documentation of this file.
1 /*
2  * Crossfire -- cooperative multi-player graphical RPG and adventure game
3  *
4  * Copyright (c) 1999-2014 Mark Wedel and the Crossfire Development Team
5  * Copyright (c) 1992 Frank Tore Johansen
6  *
7  * Crossfire is free software and comes with ABSOLUTELY NO WARRANTY. You are
8  * welcome to redistribute it under certain conditions. For details, please
9  * see COPYING and LICENSE.
10  *
11  * The authors can be reached via e-mail at <crossfire@metalforge.org>.
12  */
13 
19 #include "global.h"
20 
21 #include <stdlib.h>
22 #include <string.h>
23 
24 #include "sproto.h"
25 
26 static partylist *firstparty = NULL;
27 static partylist *lastparty = NULL;
40 partylist *party_form(object *op, const char *partyname) {
41  partylist *party;
42  char buf[MAX_BUF];
43 
44  strlcpy(buf, partyname, sizeof(buf));
46 
47  if (party_find(buf) != NULL)
48  return NULL;
49 
50  party_leave(op);
51  party = (partylist *)malloc(sizeof(partylist));
52  party->partyname = strdup_local(buf);
53 #ifdef PARTY_KILL_LOG
54  party->total_exp = 0;
55  party->kills = 0;
56 #endif
57  party->passwd[0] = '\0';
58  party->next = NULL;
59  party->partyleader = strdup_local(op->name);
61  "You have formed party: %s",
62  party->partyname);
63  op->contr->party = party;
64 
65  if (lastparty) {
66  lastparty->next = party;
67  lastparty = lastparty->next;
68  } else {
69  firstparty = party;
70  lastparty = firstparty;
71  }
72 
73  return party;
74 }
75 
85 void party_join(object *op, partylist *party) {
86  char buf[MAX_BUF];
87 
88  if (op->contr->party == party) {
90  "You are already a member of party: %s",
91  party->partyname);
92  return;
93  }
94 
95  party_leave(op);
96 
97  op->contr->party = party;
99  "You have joined party: %s\n",
100  party->partyname);
101  snprintf(buf, MAX_BUF, "%s joins party %s", op->name, party->partyname);
102  party_send_message(op, buf);
103 }
104 
108 static void remove_if_unused(partylist *party) {
109  for (player *pl = first_player; pl != NULL; pl = pl->next) {
110  if (pl->party == party)
111  return;
112  }
113  party_remove(party);
114 }
115 
123 void party_leave(object *op) {
124  char buf[MAX_BUF];
125 
126  partylist *party = op->contr->party;
127  if (party == NULL) {
128  return;
129  }
130 
132  "You leave party %s.",
133  party->partyname);
134  snprintf(buf, sizeof(buf), "%s leaves party %s.", op->name, party->partyname);
135  party_send_message(op, buf);
136  op->contr->party = NULL;
137  remove_if_unused(party);
138 }
139 
148 partylist *party_find(const char *partyname) {
149  partylist *party;
150 
151  for (party = firstparty; party; party = party->next) {
152  if (strcmp(party->partyname, partyname) == 0)
153  return party;
154  }
155  return NULL;
156 }
157 
166 void party_remove(partylist *party) {
167  partylist *tmpparty;
168  partylist *previousparty;
169  partylist *nextparty;
170 
171  if (firstparty == NULL) {
172  LOG(llevError, "party_remove: I was asked to remove party %s, but no parties are defined\n",
173  party->partyname);
174  return;
175  }
176 
177  /* special case-ism for parties at the beginning and end of the list */
178  if (party == firstparty) {
179  if (lastparty == party)
180  lastparty = NULL;
181  firstparty = firstparty->next;
182  free(party->partyleader);
183  free(party->partyname);
184  free(party);
185  return;
186  } else if (party == lastparty) {
187  for (tmpparty = firstparty; tmpparty->next != NULL; tmpparty = tmpparty->next) {
188  if (tmpparty->next == party) {
189  lastparty = tmpparty;
190  free(party->partyleader);
191  free(party->partyname);
192  free(party);
193  lastparty->next = NULL;
194  return;
195  }
196  }
197  }
198  for (tmpparty = firstparty; tmpparty->next != NULL; tmpparty = tmpparty->next)
199  if (tmpparty->next == party) {
200  previousparty = tmpparty;
201  nextparty = tmpparty->next->next;
202  /* this should be safe, because we already dealt with the lastparty case */
203 
204  previousparty->next = nextparty;
205  free(party->partyleader);
206  free(party->partyname);
207  free(party);
208  return;
209  }
210 }
211 
219  return firstparty;
220 }
221 
231  return party->next;
232 }
233 
238  partylist *party;
239  partylist *next;
240  for (party = firstparty; party != NULL; party = next) {
241  next = party->next;
242  remove_if_unused(party);
243  }
244 }
245 
254 const char *party_get_password(const partylist *party) {
255  return party->passwd;
256 }
257 
266 void party_set_password(partylist *party, const char *password) {
267  strlcpy(party->passwd, password, sizeof(party->passwd));
269 }
270 
281 int party_confirm_password(const partylist *party, const char *password) {
282  return strcmp(party->passwd, password) == 0;
283 }
284 
296 void party_send_message(object *op, const char *message) {
297  player * const self = op->contr;
298  partylist * const party = self->party;
299 
300  for (player *pl = first_player; pl != NULL; pl = pl->next)
301  if (pl->party == party && pl != self)
303  message);
304 }
305 
314 const char *party_get_leader(const partylist *party) {
315  return party->partyleader;
316 }
317 
318 #ifdef PARTY_KILL_LOG
319 
331 void party_add_kill(partylist *party, const char *killer, const char *dead, long exp) {
332  int i, pos;
333 
334  if (party->kills >= PARTY_KILL_LOG) {
335  pos = PARTY_KILL_LOG-1;
336  for (i = 0; i < PARTY_KILL_LOG-1; i++)
337  memcpy(&(party->party_kills[i]), &(party->party_kills[i+1]), sizeof(party->party_kills[0]));
338  } else
339  pos = party->kills;
340  party->kills++;
341  party->total_exp += exp;
342  party->party_kills[pos].exp = exp;
343  strncpy(party->party_kills[pos].killer, killer, MAX_NAME);
344  strncpy(party->party_kills[pos].dead, dead, MAX_NAME);
345  party->party_kills[pos].killer[MAX_NAME] = 0;
346  party->party_kills[pos].dead[MAX_NAME] = 0;
347 }
348 #endif
void draw_ext_info_format(int flags, int pri, const object *pl, uint8_t type, uint8_t subtype, const char *format,...)
Definition: main.c:316
partylist * party_get_first(void)
Definition: party.c:218
Definition: player.h:92
const char * party_get_password(const partylist *party)
Definition: party.c:254
const char * party_get_leader(const partylist *party)
Definition: party.c:314
partylist * party_find(const char *partyname)
Definition: party.c:148
static void remove_if_unused(partylist *party)
Definition: party.c:108
#define NDI_WHITE
Definition: newclient.h:222
#define strdup_local
Definition: compat.h:25
static partylist * firstparty
Definition: party.c:26
char * partyname
Definition: party.h:14
void draw_ext_info(int flags, int pri, const object *pl, uint8_t type, uint8_t subtype, const char *message)
Definition: main.c:311
partylist * party
Definition: player.h:186
static partylist * lastparty
Definition: party.c:27
int party_confirm_password(const partylist *party, const char *password)
Definition: party.c:281
partylist * party_get_next(const partylist *party)
Definition: party.c:230
void party_send_message(object *op, const char *message)
Definition: party.c:296
#define MSG_TYPE_COMMAND
Definition: newclient.h:379
#define MSG_TYPE_COMMAND_SUCCESS
Definition: newclient.h:510
#define MSG_TYPE_COMMAND_ERROR
Definition: newclient.h:509
struct party_struct * next
Definition: party.h:13
#define snprintf
Definition: win32.h:46
const char * name
Definition: object.h:311
void party_remove(partylist *party)
Definition: party.c:166
#define MSG_TYPE_COMMUNICATION
Definition: newclient.h:386
void party_leave(object *op)
Definition: party.c:123
void party_join(object *op, partylist *party)
Definition: party.c:85
struct pl * contr
Definition: object.h:276
partylist * party_form(object *op, const char *partyname)
Definition: party.c:40
#define MAX_BUF
Definition: define.h:35
void replace_unprintable_chars(char *buf)
Definition: utils.c:474
object * ob
Definition: player.h:158
void party_set_password(partylist *party, const char *password)
Definition: party.c:266
char * partyleader
Definition: party.h:11
EXTERN player * first_player
Definition: global.h:117
struct pl * next
Definition: player.h:93
#define NDI_UNIQUE
Definition: newclient.h:245
void LOG(LogLevel logLevel, const char *format,...)
Definition: logger.c:51
void party_obsolete_parties(void)
Definition: party.c:237
#define MAX_NAME
Definition: define.h:41
size_t strlcpy(char *dst, const char *src, size_t size)
Definition: porting.c:366
char passwd[9]
Definition: party.h:12
#define MSG_TYPE_COMMUNICATION_PARTY
Definition: newclient.h:622