intial version of eve that says WALL-E every so often

This commit is contained in:
Stephen Birarda 2013-04-23 13:37:49 -07:00
parent 1688e2f5c3
commit 7ae320d7e1
7 changed files with 105 additions and 46 deletions
domain-server/src
eve/src
injector/src
interface/src
libraries/shared/src

View file

@ -133,7 +133,7 @@ int main(int argc, const char * argv[])
if (DEBUG_TO_SELF ||
!agent->matches((sockaddr *)&agentPublicAddress, (sockaddr *)&agentLocalAddress, agentType)) {
if (memchr(SOLO_AGENT_TYPES_STRING, agent->getType(), 1) == NULL) {
if (memchr(SOLO_AGENT_TYPES, agent->getType(), sizeof(SOLO_AGENT_TYPES)) == NULL) {
// this is an agent of which there can be multiple, just add them to the packet
// don't send avatar agents to other avatars, that will come from avatar mixer
if (agentType != AGENT_TYPE_AVATAR || agent->getType() != AGENT_TYPE_AVATAR) {

View file

@ -13,14 +13,22 @@
#include <PacketHeaders.h>
#include <AgentList.h>
#include <AvatarData.h>
#include <AudioInjector.h>
const int EVE_AGENT_LIST_PORT = 55441;
const float DATA_SEND_INTERVAL_MSECS = 10;
const float MIN_AUDIO_SEND_INTERVAL_SECS = 10;
const int MIN_ITERATIONS_BETWEEN_AUDIO_SENDS = (MIN_AUDIO_SEND_INTERVAL_SECS * 1000) / DATA_SEND_INTERVAL_MSECS;
const int MAX_AUDIO_SEND_INTERVAL_SECS = 15;
const float MAX_ITERATIONS_BETWEEN_AUDIO_SENDS = (MAX_AUDIO_SEND_INTERVAL_SECS * 1000) / DATA_SEND_INTERVAL_MSECS;
bool stopReceiveAgentDataThread;
bool injectAudioThreadRunning = false;
void *receiveAgentData(void *args)
{
int TEMP_AUDIO_LISTEN_PORT = 55439;
UDPSocket audioSocket = UDPSocket(TEMP_AUDIO_LISTEN_PORT);
void *receiveAgentData(void *args) {
sockaddr senderAddress;
ssize_t bytesReceived;
unsigned char incomingPacket[MAX_PACKET_SIZE];
@ -54,7 +62,33 @@ void *receiveAgentData(void *args)
return NULL;
}
void *injectAudio(void *args) {
::injectAudioThreadRunning = true;
AudioInjector *eveAudioInjector = (AudioInjector *)args;
// look for an audio mixer in our agent list
Agent *audioMixer = AgentList::getInstance()->soloAgentOfType(AGENT_TYPE_AUDIO_MIXER);
if (audioMixer != NULL) {
// until the audio mixer is setup for ping-reply, activate the public socket if it's not active
if (audioMixer->getActiveSocket() == NULL) {
audioMixer->activatePublicSocket();
}
// we have an active audio mixer we can send data to
eveAudioInjector->injectAudio(&::audioSocket, audioMixer->getActiveSocket());
}
::injectAudioThreadRunning = false;
pthread_exit(0);
return NULL;
}
int main(int argc, char* argv[]) {
// new seed for random audio sleep times
srand(time(0));
// create an AgentList instance to handle communication with other agents
AgentList *agentList = AgentList::createInstance(AGENT_TYPE_AVATAR, EVE_AGENT_LIST_PORT);
@ -84,6 +118,9 @@ int main(int argc, char* argv[]) {
0.25,
eve.getBodyPosition()[2] + 0.1));
// read eve's audio data
AudioInjector eveAudioInjector = AudioInjector("eve.raw");
unsigned char broadcastPacket[MAX_PACKET_SIZE];
broadcastPacket[0] = PACKET_HEADER_HEAD_DATA;
@ -92,6 +129,9 @@ int main(int argc, char* argv[]) {
timeval thisSend;
double numMicrosecondsSleep = 0;
int numIterationsLeftBeforeAudioSend = 0;
pthread_t injectAudioThread;
while (true) {
// update the thisSend timeval to the current time
gettimeofday(&thisSend, NULL);
@ -104,11 +144,21 @@ int main(int argc, char* argv[]) {
// use the getBroadcastData method in the AvatarData class to populate the broadcastPacket buffer
numBytesToSend = eve.getBroadcastData((broadcastPacket + 1));
// use the UDPSocket instance attached to our agent list to send avatar data to mixer
agentList->getAgentSocket().send(avatarMixer->getActiveSocket(), broadcastPacket, numBytesToSend);
}
if (numIterationsLeftBeforeAudioSend == 0) {
if (!::injectAudioThreadRunning) {
pthread_create(&injectAudioThread, NULL, injectAudio, (void*) &eveAudioInjector);
numIterationsLeftBeforeAudioSend = randIntInRange(MIN_ITERATIONS_BETWEEN_AUDIO_SENDS,
MAX_ITERATIONS_BETWEEN_AUDIO_SENDS);
}
} else {
numIterationsLeftBeforeAudioSend--;
}
// sleep for the correct amount of time to have data send be consistently timed
if ((numMicrosecondsSleep = (DATA_SEND_INTERVAL_MSECS * 1000) - (usecTimestampNow() - usecTimestamp(&thisSend))) > 0) {
usleep(numMicrosecondsSleep);

View file

@ -35,8 +35,6 @@ float browThickness = 0.16;
bool usingBigSphereCollisionTest = true;
char iris_texture_file[] = "resources/images/green_eye.png";
vector<unsigned char> iris_texture;

View file

@ -24,7 +24,7 @@
using shared_lib::printLog;
const char SOLO_AGENT_TYPES_STRING[] = {
const char SOLO_AGENT_TYPES[3] = {
AGENT_TYPE_AVATAR_MIXER,
AGENT_TYPE_AUDIO_MIXER,
AGENT_TYPE_VOXEL
@ -305,8 +305,8 @@ void AgentList::handlePingReply(sockaddr *agentAddress) {
}
}
Agent* AgentList::soloAgentOfType(char agentType) {
if (memchr(SOLO_AGENT_TYPES_STRING, agentType, 1)) {
Agent* AgentList::soloAgentOfType(char agentType) {
if (memchr(SOLO_AGENT_TYPES, agentType, sizeof(SOLO_AGENT_TYPES)) != NULL) {
for(std::vector<Agent>::iterator agent = agents.begin(); agent != agents.end(); agent++) {
if (agent->getType() == agentType) {
return &*agent;

View file

@ -22,7 +22,7 @@
const int MAX_PACKET_SIZE = 1500;
const unsigned int AGENT_SOCKET_LISTEN_PORT = 40103;
const int AGENT_SILENCE_THRESHOLD_USECS = 2 * 1000000;
extern const char SOLO_AGENT_TYPES_STRING[];
extern const char SOLO_AGENT_TYPES[];
extern char DOMAIN_HOSTNAME[];
extern char DOMAIN_IP[100]; // IP Address will be re-set by lookup on startup

View file

@ -16,10 +16,11 @@
const int BUFFER_LENGTH_BYTES = 512;
const int BUFFER_LENGTH_SAMPLES = BUFFER_LENGTH_BYTES / sizeof(int16_t);
const float SAMPLE_RATE = 22050.0;
const float SAMPLE_RATE = 22050.0f;
const float BUFFER_SEND_INTERVAL_USECS = (BUFFER_LENGTH_SAMPLES / SAMPLE_RATE) * 1000000;
AudioInjector::AudioInjector(const char* filename) :
_numTotalBytesAudio(0),
_bearing(0),
_attenuationModifier(255)
{
@ -33,11 +34,18 @@ AudioInjector::AudioInjector(const char* filename) :
sourceFile.seekg(0, std::ios::end);
_numTotalBytesAudio = sourceFile.tellg();
sourceFile.seekg(0, std::ios::beg);
long sizeOfShortArray = _numTotalBytesAudio / 2;
_audioSampleArray = new int16_t[sizeOfShortArray];
if (_numTotalBytesAudio == -1) {
printf("Error reading audio data from file %s\n", filename);
_audioSampleArray = NULL;
} else {
printf("Read %d bytes from audio file\n", _numTotalBytesAudio);
sourceFile.seekg(0, std::ios::beg);
long sizeOfShortArray = _numTotalBytesAudio / 2;
_audioSampleArray = new int16_t[sizeOfShortArray];
sourceFile.read((char *)_audioSampleArray, _numTotalBytesAudio);
}
sourceFile.read((char *)_audioSampleArray, _numTotalBytesAudio);
}
AudioInjector::~AudioInjector() {
@ -51,42 +59,45 @@ void AudioInjector::setPosition(float* position) {
}
void AudioInjector::injectAudio(UDPSocket *injectorSocket, sockaddr *destinationSocket) {
timeval startTime;
// one byte for header, 3 positional floats, 1 bearing float, 1 attenuation modifier byte
int leadingBytes = 1 + (sizeof(float) * 4) + 1;
unsigned char dataPacket[BUFFER_LENGTH_BYTES + leadingBytes];
dataPacket[0] = PACKET_HEADER_INJECT_AUDIO;
unsigned char *currentPacketPtr = dataPacket + 1;
for (int i = 0; i < 3; i++) {
memcpy(currentPacketPtr, &_position[i], sizeof(float));
currentPacketPtr += sizeof(float);
}
*currentPacketPtr = _attenuationModifier;
currentPacketPtr++;
memcpy(currentPacketPtr, &_bearing, sizeof(float));
currentPacketPtr += sizeof(float);
for (int i = 0; i < _numTotalBytesAudio; i += BUFFER_LENGTH_BYTES) {
gettimeofday(&startTime, NULL);
if (_audioSampleArray != NULL) {
timeval startTime;
int numBytesToCopy = BUFFER_LENGTH_BYTES;
// one byte for header, 3 positional floats, 1 bearing float, 1 attenuation modifier byte
int leadingBytes = 1 + (sizeof(float) * 4) + 1;
unsigned char dataPacket[BUFFER_LENGTH_BYTES + leadingBytes];
if (_numTotalBytesAudio - i < BUFFER_LENGTH_BYTES) {
numBytesToCopy = _numTotalBytesAudio - i;
memset(currentPacketPtr + numBytesToCopy, 0, BUFFER_LENGTH_BYTES - numBytesToCopy);
dataPacket[0] = PACKET_HEADER_INJECT_AUDIO;
unsigned char *currentPacketPtr = dataPacket + 1;
for (int i = 0; i < 3; i++) {
memcpy(currentPacketPtr, &_position[i], sizeof(float));
currentPacketPtr += sizeof(float);
}
memcpy(currentPacketPtr, _audioSampleArray + (i / 2), numBytesToCopy);
injectorSocket->send(destinationSocket, dataPacket, sizeof(dataPacket));
*currentPacketPtr = _attenuationModifier;
currentPacketPtr++;
double usecToSleep = BUFFER_SEND_INTERVAL_USECS - (usecTimestampNow() - usecTimestamp(&startTime));
if (usecToSleep > 0) {
usleep(usecToSleep);
memcpy(currentPacketPtr, &_bearing, sizeof(float));
currentPacketPtr += sizeof(float);
for (int i = 0; i < _numTotalBytesAudio; i += BUFFER_LENGTH_BYTES) {
gettimeofday(&startTime, NULL);
int numBytesToCopy = BUFFER_LENGTH_BYTES;
if (_numTotalBytesAudio - i < BUFFER_LENGTH_BYTES) {
numBytesToCopy = _numTotalBytesAudio - i;
memset(currentPacketPtr + numBytesToCopy, 0, BUFFER_LENGTH_BYTES - numBytesToCopy);
}
memcpy(currentPacketPtr, _audioSampleArray + (i / 2), numBytesToCopy);
injectorSocket->send(destinationSocket, dataPacket, sizeof(dataPacket));
double usecToSleep = BUFFER_SEND_INTERVAL_USECS - (usecTimestampNow() - usecTimestamp(&startTime));
if (usecToSleep > 0) {
usleep(usecToSleep);
}
}
}
}