mirror of
https://thingvellir.net/git/overte
synced 2025-03-27 23:52:03 +01:00
Merge branch 'master' of git://github.com/worklist/interface
Conflicts: main.cpp
This commit is contained in:
commit
20ae9e0f11
13 changed files with 448 additions and 629 deletions
87
agent.cpp
Normal file
87
agent.cpp
Normal file
|
@ -0,0 +1,87 @@
|
|||
//
|
||||
// agent.cpp
|
||||
// interface
|
||||
//
|
||||
// Created by Philip Rosedale on 11/20/12.
|
||||
// Copyright (c) 2012 __MyCompanyName__. All rights reserved.
|
||||
//
|
||||
|
||||
#include <iostream>
|
||||
#include "agent.h"
|
||||
|
||||
// Structure to hold references to other agents that are nearby
|
||||
|
||||
const int MAX_AGENTS = 100;
|
||||
struct AgentList {
|
||||
in_addr sin_addr;
|
||||
glm::vec3 position;
|
||||
} agents[MAX_AGENTS];
|
||||
int num_agents = 0;
|
||||
|
||||
//
|
||||
// Process an incoming spaceserver packet telling you about other nearby agents
|
||||
//
|
||||
void update_agents(char * data, int length) {
|
||||
std::string packet(data, length);
|
||||
//std::string packet("127.0.0.1,");
|
||||
//std::cout << " Update Agents, string: " << packet << "\n";
|
||||
size_t spot;
|
||||
size_t start_spot = 0;
|
||||
spot = packet.find_first_of (",", 0);
|
||||
while (spot != std::string::npos) {
|
||||
std::string IPstring = packet.substr(start_spot, spot-start_spot);
|
||||
//std::cout << "Found " << num_agents <<
|
||||
//" with IP " << IPstring << " from " << start_spot << " to " << spot << "\n";
|
||||
// Add the IP address to the agent table
|
||||
add_agent(&IPstring);
|
||||
start_spot = spot + 1;
|
||||
if (start_spot < packet.length())
|
||||
spot = packet.find_first_of (",", start_spot);
|
||||
else spot = std::string::npos;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Look for an agent by it's IP number, add if it does not exist in local list
|
||||
//
|
||||
int add_agent(std::string * IP) {
|
||||
in_addr_t addr = inet_addr(IP->c_str());
|
||||
//std::cout << "Checking for " << IP->c_str() << " ";
|
||||
for (int i = 0; i < num_agents; i++) {
|
||||
if (agents[i].sin_addr.s_addr == addr) {
|
||||
//std::cout << "Found!\n";
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
if (num_agents < MAX_AGENTS) {
|
||||
agents[num_agents].sin_addr.s_addr = addr;
|
||||
std::cout << "Added Agent # " << num_agents << " with IP " <<
|
||||
inet_ntoa(agents[num_agents].sin_addr) << "\n";
|
||||
num_agents++;
|
||||
return 1;
|
||||
} else {
|
||||
std::cout << "Max agents reached fail!\n";
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Broadcast data to all the other agents you are aware of, returns 1 for success
|
||||
//
|
||||
int broadcast(int handle, char * data, int length) {
|
||||
sockaddr_in dest_address;
|
||||
dest_address.sin_family = AF_INET;
|
||||
dest_address.sin_port = htons( (unsigned short) UDP_PORT );
|
||||
|
||||
int sent_bytes;
|
||||
for (int i = 0; i < num_agents; i++) {
|
||||
dest_address.sin_addr.s_addr = agents[i].sin_addr.s_addr;
|
||||
sent_bytes = sendto( handle, (const char*)data, length,
|
||||
0, (sockaddr*)&dest_address, sizeof(sockaddr_in) );
|
||||
if (sent_bytes != length) {
|
||||
std::cout << "Broadcast packet fail!\n";
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
24
agent.h
Normal file
24
agent.h
Normal file
|
@ -0,0 +1,24 @@
|
|||
//
|
||||
// agent.h
|
||||
// interface
|
||||
//
|
||||
// Created by Philip Rosedale on 11/20/12.
|
||||
// Copyright (c) 2012 __MyCompanyName__. All rights reserved.
|
||||
//
|
||||
|
||||
#ifndef interface_agent_h
|
||||
#define interface_agent_h
|
||||
|
||||
#include "glm/glm.hpp"
|
||||
#include <sys/socket.h>
|
||||
#include <netinet/in.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <fcntl.h>
|
||||
#include <string.h>
|
||||
#include "network.h"
|
||||
|
||||
void update_agents(char * data, int length);
|
||||
int add_agent(std::string * IP);
|
||||
int broadcast(int handle, char * data, int length);
|
||||
|
||||
#endif
|
119
head.cpp
119
head.cpp
|
@ -62,6 +62,125 @@ void readSensors()
|
|||
|
||||
}
|
||||
|
||||
/*
|
||||
void update_pos(float frametime)
|
||||
// Using serial data, update avatar/render position and angles
|
||||
{
|
||||
float measured_pitch_rate = adc_channels[0] - avg_adc_channels[0];
|
||||
float measured_yaw_rate = adc_channels[1] - avg_adc_channels[1];
|
||||
float measured_lateral_accel = adc_channels[3] - avg_adc_channels[3];
|
||||
float measured_fwd_accel = avg_adc_channels[2] - adc_channels[2];
|
||||
|
||||
// Update avatar head position based on measured gyro rates
|
||||
const float HEAD_ROTATION_SCALE = 0.20;
|
||||
const float HEAD_LEAN_SCALE = 0.02;
|
||||
if (head_mirror) {
|
||||
myHead.addYaw(measured_yaw_rate * HEAD_ROTATION_SCALE * frametime);
|
||||
myHead.addPitch(measured_pitch_rate * -HEAD_ROTATION_SCALE * frametime);
|
||||
myHead.addLean(measured_lateral_accel * frametime * HEAD_LEAN_SCALE, measured_fwd_accel*frametime * HEAD_LEAN_SCALE);
|
||||
} else {
|
||||
myHead.addYaw(measured_yaw_rate * -HEAD_ROTATION_SCALE * frametime);
|
||||
myHead.addPitch(measured_pitch_rate * -HEAD_ROTATION_SCALE * frametime);
|
||||
myHead.addLean(measured_lateral_accel * frametime * -HEAD_LEAN_SCALE, measured_fwd_accel*frametime * HEAD_LEAN_SCALE);
|
||||
}
|
||||
// Decay avatar head back toward zero
|
||||
//pitch *= (1.f - 5.0*frametime);
|
||||
//yaw *= (1.f - 7.0*frametime);
|
||||
|
||||
// Update head_mouse model
|
||||
const float MIN_MOUSE_RATE = 30.0;
|
||||
const float MOUSE_SENSITIVITY = 0.1;
|
||||
if (powf(measured_yaw_rate*measured_yaw_rate +
|
||||
measured_pitch_rate*measured_pitch_rate, 0.5) > MIN_MOUSE_RATE)
|
||||
{
|
||||
head_mouse_x -= measured_yaw_rate*MOUSE_SENSITIVITY;
|
||||
head_mouse_y += measured_pitch_rate*MOUSE_SENSITIVITY*(float)HEIGHT/(float)WIDTH;
|
||||
}
|
||||
head_mouse_x = max(head_mouse_x, 0);
|
||||
head_mouse_x = min(head_mouse_x, WIDTH);
|
||||
head_mouse_y = max(head_mouse_y, 0);
|
||||
head_mouse_y = min(head_mouse_y, HEIGHT);
|
||||
|
||||
// Update render direction (pitch/yaw) based on measured gyro rates
|
||||
const int MIN_YAW_RATE = 300;
|
||||
const float YAW_SENSITIVITY = 0.03;
|
||||
const int MIN_PITCH_RATE = 300;
|
||||
const float PITCH_SENSITIVITY = 0.04;
|
||||
|
||||
if (fabs(measured_yaw_rate) > MIN_YAW_RATE)
|
||||
{
|
||||
if (measured_yaw_rate > 0)
|
||||
render_yaw_rate -= (measured_yaw_rate - MIN_YAW_RATE) * YAW_SENSITIVITY * frametime;
|
||||
else
|
||||
render_yaw_rate -= (measured_yaw_rate + MIN_YAW_RATE) * YAW_SENSITIVITY * frametime;
|
||||
}
|
||||
if (fabs(measured_pitch_rate) > MIN_PITCH_RATE)
|
||||
{
|
||||
if (measured_pitch_rate > 0)
|
||||
render_pitch_rate += (measured_pitch_rate - MIN_PITCH_RATE) * PITCH_SENSITIVITY * frametime;
|
||||
else
|
||||
render_pitch_rate += (measured_pitch_rate + MIN_PITCH_RATE) * PITCH_SENSITIVITY * frametime;
|
||||
}
|
||||
render_yaw += render_yaw_rate;
|
||||
render_pitch += render_pitch_rate;
|
||||
|
||||
// Decay render_pitch toward zero because we never look constantly up/down
|
||||
render_pitch *= (1.f - 2.0*frametime);
|
||||
|
||||
// Decay angular rates toward zero
|
||||
render_pitch_rate *= (1.f - 5.0*frametime);
|
||||
render_yaw_rate *= (1.f - 7.0*frametime);
|
||||
|
||||
// Update slide left/right based on accelerometer reading
|
||||
const int MIN_LATERAL_ACCEL = 20;
|
||||
const float LATERAL_SENSITIVITY = 0.001;
|
||||
if (fabs(measured_lateral_accel) > MIN_LATERAL_ACCEL)
|
||||
{
|
||||
if (measured_lateral_accel > 0)
|
||||
lateral_vel += (measured_lateral_accel - MIN_LATERAL_ACCEL) * LATERAL_SENSITIVITY * frametime;
|
||||
else
|
||||
lateral_vel += (measured_lateral_accel + MIN_LATERAL_ACCEL) * LATERAL_SENSITIVITY * frametime;
|
||||
}
|
||||
|
||||
//slide += lateral_vel;
|
||||
lateral_vel *= (1.f - 4.0*frametime);
|
||||
|
||||
// Update fwd/back based on accelerometer reading
|
||||
const int MIN_FWD_ACCEL = 20;
|
||||
const float FWD_SENSITIVITY = 0.001;
|
||||
|
||||
if (fabs(measured_fwd_accel) > MIN_FWD_ACCEL)
|
||||
{
|
||||
if (measured_fwd_accel > 0)
|
||||
fwd_vel += (measured_fwd_accel - MIN_FWD_ACCEL) * FWD_SENSITIVITY * frametime;
|
||||
else
|
||||
fwd_vel += (measured_fwd_accel + MIN_FWD_ACCEL) * FWD_SENSITIVITY * frametime;
|
||||
|
||||
}
|
||||
// Decrease forward velocity
|
||||
fwd_vel *= (1.f - 4.0*frametime);
|
||||
|
||||
// Update forward vector based on pitch and yaw
|
||||
fwd_vec[0] = -sinf(render_yaw*PI/180);
|
||||
fwd_vec[1] = sinf(render_pitch*PI/180);
|
||||
fwd_vec[2] = cosf(render_yaw*PI/180);
|
||||
|
||||
// Advance location forward
|
||||
location[0] += fwd_vec[0]*fwd_vel;
|
||||
location[1] += fwd_vec[1]*fwd_vel;
|
||||
location[2] += fwd_vec[2]*fwd_vel;
|
||||
|
||||
// Slide location sideways
|
||||
location[0] += fwd_vec[2]*-lateral_vel;
|
||||
location[2] += fwd_vec[0]*lateral_vel;
|
||||
|
||||
// Update head and manipulator objects with object with current location
|
||||
myHead.setPos(glm::vec3(location[0], location[1], location[2]));
|
||||
balls.updateHand(myHead.getPos() + myHand.getPos(), glm::vec3(0,0,0), myHand.getRadius());
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
void Head::addLean(float x, float z) {
|
||||
// Add Body lean as impulse
|
||||
leanSideways += x;
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
B6BDADE415F44AC7002A07DF /* AudioUnit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B6BDADDC15F444D3002A07DF /* AudioUnit.framework */; };
|
||||
B6BDAE4415F6BE53002A07DF /* particle.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B6BDAE4315F6BE53002A07DF /* particle.cpp */; };
|
||||
D409B98A165849180099B0B3 /* cloud.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D409B989165849180099B0B3 /* cloud.cpp */; };
|
||||
D409B9A8165CA7BC0099B0B3 /* agent.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D409B9A7165CA7BB0099B0B3 /* agent.cpp */; };
|
||||
D40BDFD513404BA300B0BE1F /* GLUT.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = D40BDFD413404BA300B0BE1F /* GLUT.framework */; };
|
||||
D40BDFD713404BB300B0BE1F /* OpenGL.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = D40BDFD613404BB300B0BE1F /* OpenGL.framework */; };
|
||||
D40FD5FB164AF1C200878184 /* int-texture256-v2.png in CopyFiles */ = {isa = PBXBuildFile; fileRef = D40FD5FA164AF1A700878184 /* int-texture256-v2.png */; };
|
||||
|
@ -69,6 +70,8 @@
|
|||
C6859E8B029090EE04C91782 /* test_c_plus.1 */ = {isa = PBXFileReference; lastKnownFileType = text.man; path = test_c_plus.1; sourceTree = "<group>"; };
|
||||
D409B988165849030099B0B3 /* cloud.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = cloud.h; sourceTree = "<group>"; };
|
||||
D409B989165849180099B0B3 /* cloud.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = cloud.cpp; sourceTree = "<group>"; };
|
||||
D409B9A6165CA7A50099B0B3 /* agent.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = agent.h; sourceTree = "<group>"; };
|
||||
D409B9A7165CA7BB0099B0B3 /* agent.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = agent.cpp; sourceTree = "<group>"; };
|
||||
D40BDFD413404BA300B0BE1F /* GLUT.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = GLUT.framework; path = /System/Library/Frameworks/GLUT.framework; sourceTree = "<absolute>"; };
|
||||
D40BDFD613404BB300B0BE1F /* OpenGL.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = OpenGL.framework; path = /System/Library/Frameworks/OpenGL.framework; sourceTree = "<absolute>"; };
|
||||
D40FD5FA164AF1A700878184 /* int-texture256-v2.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "int-texture256-v2.png"; sourceTree = SOURCE_ROOT; };
|
||||
|
@ -137,6 +140,8 @@
|
|||
isa = PBXGroup;
|
||||
children = (
|
||||
08FB7796FE84155DC02AAC07 /* main.cpp */,
|
||||
D409B9A6165CA7A50099B0B3 /* agent.h */,
|
||||
D409B9A7165CA7BB0099B0B3 /* agent.cpp */,
|
||||
D409B988165849030099B0B3 /* cloud.h */,
|
||||
D409B989165849180099B0B3 /* cloud.cpp */,
|
||||
D4EE3BC015E746E900EE4C89 /* world.h */,
|
||||
|
@ -230,6 +235,7 @@
|
|||
isa = PBXProject;
|
||||
attributes = {
|
||||
LastUpgradeCheck = 0430;
|
||||
ORGANIZATIONNAME = "Rosedale Lab";
|
||||
};
|
||||
buildConfigurationList = 1DEB923508733DC60010E9CD /* Build configuration list for PBXProject "interface" */;
|
||||
compatibilityVersion = "Xcode 3.2";
|
||||
|
@ -267,6 +273,7 @@
|
|||
F68135561648617D003040E3 /* texture.cpp in Sources */,
|
||||
F681358B1648896D003040E3 /* lodepng.cpp in Sources */,
|
||||
D409B98A165849180099B0B3 /* cloud.cpp in Sources */,
|
||||
D409B9A8165CA7BC0099B0B3 /* agent.cpp in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
|
|
Binary file not shown.
|
@ -16,5 +16,18 @@
|
|||
landmarkName = "field_avg_neighbors(int index, glm::vec3 * result)"
|
||||
landmarkType = "7">
|
||||
</FileBreakpoint>
|
||||
<FileBreakpoint
|
||||
shouldBeEnabled = "No"
|
||||
ignoreCount = "0"
|
||||
continueAfterRunningActions = "No"
|
||||
filePath = "util.cpp"
|
||||
timestampString = "375575185.217506"
|
||||
startingColumnNumber = "9223372036854775807"
|
||||
endingColumnNumber = "9223372036854775807"
|
||||
startingLineNumber = "28"
|
||||
endingLineNumber = "28"
|
||||
landmarkName = "makeCubes(float location[3], float scale, int * index, float * cubes_position, float * cubes_scale, float * cubes_color)"
|
||||
landmarkType = "7">
|
||||
</FileBreakpoint>
|
||||
</FileBreakpoints>
|
||||
</Bucket>
|
||||
|
|
241
main.cpp
241
main.cpp
|
@ -33,7 +33,6 @@
|
|||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <termios.h>
|
||||
#include "tga.h" // Texture loader library
|
||||
#include "glm/glm.hpp"
|
||||
#include <portaudio.h>
|
||||
|
||||
|
@ -46,10 +45,10 @@
|
|||
#include "head.h"
|
||||
#include "hand.h"
|
||||
#include "particle.h"
|
||||
|
||||
#include "texture.h"
|
||||
|
||||
#include "cloud.h"
|
||||
#include "agent.h"
|
||||
|
||||
|
||||
//TGAImg Img;
|
||||
|
||||
|
@ -60,7 +59,7 @@ int serial_on = 0; // Is serial connection on/off? System wil
|
|||
int audio_on = 0; // Whether to turn on the audio support
|
||||
int simulate_on = 1;
|
||||
|
||||
// Network Socket Stuff
|
||||
// Network Socket Stuff
|
||||
// For testing, add milliseconds of delay for received UDP packets
|
||||
int UDP_socket;
|
||||
int delay = 0;
|
||||
|
@ -79,16 +78,9 @@ int target_display = 0;
|
|||
|
||||
int head_mirror = 0; // Whether to mirror the head when viewing it
|
||||
|
||||
unsigned char last_key = 0;
|
||||
|
||||
double ping = 0;
|
||||
|
||||
int WIDTH = 1200;
|
||||
int HEIGHT = 800;
|
||||
|
||||
#define BOTTOM_MARGIN 0
|
||||
#define RIGHT_MARGIN 0
|
||||
|
||||
#define HAND_RADIUS 0.25 // Radius of in-world 'hand' of you
|
||||
Head myHead; // The rendered head of oneself or others
|
||||
Hand myHand(HAND_RADIUS,
|
||||
|
@ -103,33 +95,20 @@ ParticleSystem balls(0,
|
|||
0.0 // Gravity
|
||||
);
|
||||
|
||||
Cloud cloud(250000, // Particles
|
||||
Cloud cloud(0, // Particles
|
||||
box, // Bounding Box
|
||||
false // Wrap
|
||||
);
|
||||
|
||||
// FIELD INFORMATION
|
||||
// If the simulation 'world' is a box with 10M boundaries, the offset to a field cell is given by:
|
||||
// element = [x/10 + (y/10)*10 + (z*/10)*100]
|
||||
//
|
||||
// The vec(x,y,z) corner of a field cell at element i is:
|
||||
//
|
||||
// z = (int)( i / 100)
|
||||
// y = (int)(i % 100 / 10)
|
||||
// x = (int)(i % 10)
|
||||
float cubes_position[MAX_CUBES*3];
|
||||
float cubes_scale[MAX_CUBES];
|
||||
float cubes_color[MAX_CUBES*3];
|
||||
int cube_count = 0;
|
||||
|
||||
#define RENDER_FRAME_MSECS 10
|
||||
#define SLEEP 0
|
||||
|
||||
#define NUM_TRIS 0
|
||||
|
||||
struct {
|
||||
float vertices[NUM_TRIS * 3];
|
||||
float vel [NUM_TRIS * 3];
|
||||
}tris;
|
||||
|
||||
|
||||
float yaw =0.f; // The yaw, pitch for the avatar head
|
||||
float yaw =0.f; // The yaw, pitch for the avatar head
|
||||
float pitch = 0.f; //
|
||||
float start_yaw = 90.0;
|
||||
float render_yaw = start_yaw;
|
||||
|
@ -165,7 +144,6 @@ int head_lean_x, head_lean_y;
|
|||
int mouse_x, mouse_y; // Where is the mouse
|
||||
int mouse_pressed = 0; // true if mouse has been pressed (clear when finished)
|
||||
|
||||
int accel_x, accel_y;
|
||||
|
||||
int speed;
|
||||
|
||||
|
@ -224,6 +202,10 @@ void Timer(int extra)
|
|||
|
||||
glutTimerFunc(1000,Timer,0);
|
||||
gettimeofday(&timer_start, NULL);
|
||||
|
||||
// Send a message to the spaceserver telling it we are ALIVE
|
||||
notify_spaceserver(UDP_socket, location[0], location[1], location[2]);
|
||||
|
||||
}
|
||||
|
||||
void display_stats(void)
|
||||
|
@ -265,10 +247,7 @@ void initDisplay(void)
|
|||
|
||||
void init(void)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
load_png_as_texture(texture_filename);
|
||||
printf("Texture loaded.\n");
|
||||
int i;
|
||||
|
||||
if (audio_on) {
|
||||
Audio::init();
|
||||
|
@ -297,42 +276,20 @@ void init(void)
|
|||
myHead.setNoise(noise);
|
||||
}
|
||||
|
||||
// Init particles
|
||||
float tri_scale, r;
|
||||
const float VEL_SCALE = 0.00;
|
||||
for (i = 0; i < NUM_TRIS; i++)
|
||||
{
|
||||
r = randFloat();
|
||||
if (r > .999) tri_scale = 0.7;
|
||||
else if (r > 0.90) tri_scale = 0.1;
|
||||
else tri_scale = 0.05;
|
||||
|
||||
|
||||
glm::vec3 pos (randFloat() * WORLD_SIZE,
|
||||
randFloat() * WORLD_SIZE,
|
||||
randFloat() * WORLD_SIZE);
|
||||
glm::vec3 verts[3];
|
||||
verts[j].x = pos.x + randFloat() * tri_scale - tri_scale/2.f;
|
||||
verts[j].y = pos.y + randFloat() * tri_scale - tri_scale/2.f;
|
||||
verts[j].z = pos.z + randFloat() * tri_scale - tri_scale/2.f;
|
||||
tris.vertices[i*3] = verts[j].x;
|
||||
tris.vertices[i*3 + 1] = verts[j].y;
|
||||
tris.vertices[i*3 + 2] = verts[j].z;
|
||||
|
||||
// reuse pos for the normal
|
||||
//glm::normalize((pos += glm::cross(verts[1] - verts[0], verts[2] - verts[0])));
|
||||
//tris.normals[i*3] = pos.x;
|
||||
//tris.normals[i*3+1] = pos.y;
|
||||
//tris.normals[i*3+2] = pos.z;
|
||||
|
||||
// Moving - white
|
||||
//tris.colors[i*3] = 1.0; tris.colors[i*3+1] = 1.0; tris.colors[i*3+2] = 1.0;
|
||||
tris.vel[i*3] = (randFloat() - 0.5)*VEL_SCALE;
|
||||
tris.vel[i*3+1] = (randFloat() - 0.5)*VEL_SCALE;
|
||||
tris.vel[i*3+2] = (randFloat() - 0.5)*VEL_SCALE;
|
||||
|
||||
int index = 0;
|
||||
float location[] = {0,0,0};
|
||||
float scale = 10.0;
|
||||
int j = 0;
|
||||
while (index < (MAX_CUBES/2)) {
|
||||
index = 0;
|
||||
j++;
|
||||
makeCubes(location, scale, &index, cubes_position, cubes_scale, cubes_color);
|
||||
std::cout << "Run " << j << " Made " << index << " cubes\n";
|
||||
cube_count = index;
|
||||
}
|
||||
|
||||
//load_png_as_texture(texture_filename);
|
||||
|
||||
if (serial_on)
|
||||
{
|
||||
// Call readsensors for a while to get stable initial values on sensors
|
||||
|
@ -364,57 +321,6 @@ void terminate () {
|
|||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
const float SCALE_SENSORS = 0.3f;
|
||||
const float SCALE_X = 2.f;
|
||||
const float SCALE_Y = 1.f;
|
||||
|
||||
|
||||
void update_tris()
|
||||
{
|
||||
int i, j;
|
||||
float field_val[3];
|
||||
float field_contrib[3];
|
||||
for (i = 0; i < NUM_TRIS; i++)
|
||||
{
|
||||
// Update position
|
||||
tris.vertices[i*3+0] += tris.vel[i*3];
|
||||
tris.vertices[i*3+1] += tris.vel[i*3+1];
|
||||
tris.vertices[i*3+2] += tris.vel[i*3+2];
|
||||
|
||||
// Add a little gravity
|
||||
//tris.vel[i*3+1] -= 0.0001;
|
||||
|
||||
const float DRAG = 0.99;
|
||||
// Drag: Decay velocity
|
||||
tris.vel[i*3] *= DRAG;
|
||||
tris.vel[i*3+1] *= DRAG;
|
||||
tris.vel[i*3+2] *= DRAG;
|
||||
|
||||
// Read and add velocity from field
|
||||
field_value(field_val, &tris.vertices[i*3]);
|
||||
tris.vel[i*3] += field_val[0];
|
||||
tris.vel[i*3+1] += field_val[1];
|
||||
tris.vel[i*3+2] += field_val[2];
|
||||
|
||||
// Add a tiny bit of energy back to the field
|
||||
const float FIELD_COUPLE = 0.0000001;
|
||||
field_contrib[0] = tris.vel[i*3]*FIELD_COUPLE;
|
||||
field_contrib[1] = tris.vel[i*3+1]*FIELD_COUPLE;
|
||||
field_contrib[2] = tris.vel[i*3+2]*FIELD_COUPLE;
|
||||
field_add(field_contrib, &tris.vertices[i*3]);
|
||||
|
||||
|
||||
// bounce at edge of world
|
||||
for (j=0; j < 3; j++) {
|
||||
if ((tris.vertices[i*3+j] > WORLD_SIZE) || (tris.vertices[i*3+j] < 0.0)) {
|
||||
tris.vertices[i*3+j] = min(WORLD_SIZE, tris.vertices[i*3+j]);
|
||||
tris.vertices[i*3+j] = max(0.f, tris.vertices[i*3+j]);
|
||||
tris.vel[i*3 + j]*= -1.0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void reset_sensors()
|
||||
{
|
||||
//
|
||||
|
@ -447,7 +353,7 @@ void update_pos(float frametime)
|
|||
float measured_fwd_accel = avg_adc_channels[2] - adc_channels[2];
|
||||
|
||||
// Update avatar head position based on measured gyro rates
|
||||
const float HEAD_ROTATION_SCALE = 0.10;
|
||||
const float HEAD_ROTATION_SCALE = 0.20;
|
||||
const float HEAD_LEAN_SCALE = 0.02;
|
||||
if (head_mirror) {
|
||||
myHead.addYaw(measured_yaw_rate * HEAD_ROTATION_SCALE * frametime);
|
||||
|
@ -566,13 +472,16 @@ void update_pos(float frametime)
|
|||
// Update head and manipulator objects with object with current location
|
||||
myHead.setPos(glm::vec3(location[0], location[1], location[2]));
|
||||
balls.updateHand(myHead.getPos() + myHand.getPos(), glm::vec3(0,0,0), myHand.getRadius());
|
||||
|
||||
// Update all this stuff to any agents that are nearby and need to see it!
|
||||
char test[] = "BXXX";
|
||||
broadcast(UDP_socket, test, strlen(test));
|
||||
}
|
||||
|
||||
void display(void)
|
||||
{
|
||||
|
||||
int i;
|
||||
|
||||
|
||||
glEnable (GL_DEPTH_TEST);
|
||||
glEnable(GL_LIGHTING);
|
||||
glEnable(GL_LINE_SMOOTH);
|
||||
|
@ -599,30 +508,27 @@ void display(void)
|
|||
glRotatef(render_pitch, 1, 0, 0);
|
||||
glRotatef(render_yaw, 0, 1, 0);
|
||||
glTranslatef(location[0], location[1], location[2]);
|
||||
|
||||
glPushMatrix();
|
||||
glTranslatef(WORLD_SIZE/2, WORLD_SIZE/2, WORLD_SIZE/2);
|
||||
int i = 0;
|
||||
while (i < cube_count) {
|
||||
glPushMatrix();
|
||||
glTranslatef(cubes_position[i*3], cubes_position[i*3+1], cubes_position[i*3+2]);
|
||||
glColor3fv(&cubes_color[i*3]);
|
||||
glutSolidCube(cubes_scale[i]);
|
||||
glPopMatrix();
|
||||
i++;
|
||||
}
|
||||
glPopMatrix();
|
||||
|
||||
|
||||
/* Draw Point Sprites */
|
||||
|
||||
//glActiveTexture(GL_TEXTURE0);
|
||||
glEnable( GL_TEXTURE_2D );
|
||||
|
||||
//glTexEnvi(GL_POINT_SPRITE, GL_COORD_REPLACE, GL_TRUE);
|
||||
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
|
||||
glPointParameterfvARB( GL_POINT_DISTANCE_ATTENUATION_ARB, particle_attenuation_quadratic );
|
||||
|
||||
float maxSize = 0.0f;
|
||||
glGetFloatv( GL_POINT_SIZE_MAX_ARB, &maxSize );
|
||||
glPointSize( maxSize );
|
||||
glPointParameterfARB( GL_POINT_SIZE_MAX_ARB, maxSize );
|
||||
glPointParameterfARB( GL_POINT_SIZE_MIN_ARB, 0.001f );
|
||||
load_png_as_texture(texture_filename);
|
||||
|
||||
glTexEnvf( GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE );
|
||||
glEnable( GL_POINT_SPRITE_ARB );
|
||||
if (!display_head) {
|
||||
glDrawElements(GL_POINTS, NUM_TRIS, GL_FLOAT, tris.vertices);
|
||||
}
|
||||
glDisable( GL_POINT_SPRITE_ARB );
|
||||
glDisable( GL_TEXTURE_2D );
|
||||
|
||||
if (!display_head) cloud.render();
|
||||
// Show field vectors
|
||||
if (display_field) field_render();
|
||||
|
@ -636,9 +542,13 @@ void display(void)
|
|||
|
||||
// Render the world box
|
||||
if (!display_head) render_world_box();
|
||||
|
||||
glm::vec3 test(0.5, 0.5, 0.5);
|
||||
render_vector(&test);
|
||||
|
||||
glPopMatrix();
|
||||
|
||||
|
||||
// Render 2D overlay: I/O level bar graphs and text
|
||||
glMatrixMode(GL_PROJECTION);
|
||||
glPushMatrix();
|
||||
|
@ -708,14 +618,24 @@ void display(void)
|
|||
glutSwapBuffers();
|
||||
framecount++;
|
||||
}
|
||||
|
||||
void specialkey(int k, int x, int y)
|
||||
{
|
||||
if (k == GLUT_KEY_UP) fwd_vel += 0.05;
|
||||
if (k == GLUT_KEY_DOWN) fwd_vel -= 0.05;
|
||||
if (k == GLUT_KEY_LEFT) {
|
||||
if (glutGetModifiers() == GLUT_ACTIVE_SHIFT) lateral_vel -= 0.02;
|
||||
else render_yaw_rate -= 0.25;
|
||||
}
|
||||
if (k == GLUT_KEY_RIGHT) {
|
||||
if (glutGetModifiers() == GLUT_ACTIVE_SHIFT) lateral_vel += 0.02;
|
||||
else render_yaw_rate += 0.25;
|
||||
}
|
||||
|
||||
}
|
||||
void key(unsigned char k, int x, int y)
|
||||
{
|
||||
// Process keypresses
|
||||
|
||||
last_key = k;
|
||||
|
||||
if (k == 'q') ::terminate();
|
||||
if (k == 'q') ::terminate();
|
||||
if (k == '/') stats_on = !stats_on; // toggle stats
|
||||
if (k == 'n')
|
||||
{
|
||||
|
@ -761,6 +681,9 @@ void key(unsigned char k, int x, int y)
|
|||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Check for and process incoming network packets
|
||||
//
|
||||
void read_network()
|
||||
{
|
||||
// Receive packets
|
||||
|
@ -771,15 +694,29 @@ void read_network()
|
|||
bytescount += bytes_recvd;
|
||||
// If packet is a Mouse data packet, copy it over
|
||||
if (incoming_packet[0] == 'M') {
|
||||
//
|
||||
// mouse location packet
|
||||
//
|
||||
sscanf(incoming_packet, "M %d %d", &target_x, &target_y);
|
||||
target_display = 1;
|
||||
printf("X = %d Y = %d\n", target_x, target_y);
|
||||
} else if (incoming_packet[0] == 'P') {
|
||||
// Ping packet - check time and record
|
||||
//
|
||||
// Ping packet - check time and record
|
||||
//
|
||||
timeval check;
|
||||
gettimeofday(&check, NULL);
|
||||
ping_msecs = (float)diffclock(ping_start, check);
|
||||
|
||||
} else if (incoming_packet[0] == 'S') {
|
||||
//
|
||||
// Message from Spaceserver
|
||||
//
|
||||
update_agents(&incoming_packet[1], bytes_recvd - 1);
|
||||
} else if (incoming_packet[0] == 'B') {
|
||||
//
|
||||
// Broadcast packet from another agent
|
||||
//
|
||||
//std::cout << "Got broadcast from agent\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -795,7 +732,6 @@ void idle(void)
|
|||
// Simulation
|
||||
update_pos(1.f/FPS);
|
||||
if (simulate_on) {
|
||||
update_tris();
|
||||
field_simulate(1.f/FPS);
|
||||
myHead.simulate(1.f/FPS);
|
||||
myHand.simulate(1.f/FPS);
|
||||
|
@ -836,8 +772,8 @@ void reshape(int width, int height)
|
|||
glLoadIdentity();
|
||||
gluPerspective(45, //view angle
|
||||
1.0, //aspect ratio
|
||||
1.0, //near clip
|
||||
200.0);//far clip
|
||||
0.1, //near clip
|
||||
50.0);//far clip
|
||||
glMatrixMode(GL_MODELVIEW);
|
||||
glLoadIdentity();
|
||||
|
||||
|
@ -908,7 +844,7 @@ int main(int argc, char** argv)
|
|||
|
||||
glutInit(&argc, argv);
|
||||
glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);
|
||||
glutInitWindowSize(RIGHT_MARGIN + WIDTH, BOTTOM_MARGIN + HEIGHT);
|
||||
glutInitWindowSize(WIDTH, HEIGHT);
|
||||
glutCreateWindow("Interface");
|
||||
|
||||
printf( "Created Display Window.\n" );
|
||||
|
@ -918,6 +854,7 @@ int main(int argc, char** argv)
|
|||
glutDisplayFunc(display);
|
||||
glutReshapeFunc(reshape);
|
||||
glutKeyboardFunc(key);
|
||||
glutSpecialFunc(specialkey);
|
||||
glutMotionFunc(motionFunc);
|
||||
glutMouseFunc(mouseFunc);
|
||||
glutIdleFunc(idle);
|
||||
|
|
27
network.cpp
27
network.cpp
|
@ -11,9 +11,6 @@
|
|||
#include "network.h"
|
||||
|
||||
|
||||
const int UDP_PORT = 30000;
|
||||
const char DESTINATION_IP[] = "127.0.0.1";
|
||||
|
||||
// Implementation of optional delay behavior using a ring buffer
|
||||
const int MAX_DELAY_PACKETS = 300;
|
||||
char delay_buffer[MAX_PACKET_SIZE*MAX_DELAY_PACKETS];
|
||||
|
@ -22,7 +19,7 @@ int delay_size_received[MAX_DELAY_PACKETS];
|
|||
int next_to_receive = 0;
|
||||
int next_to_send = 0;
|
||||
|
||||
sockaddr_in address, dest_address, from;
|
||||
sockaddr_in address, dest_address, spaceserver_address, from;
|
||||
socklen_t fromLength = sizeof( from );
|
||||
|
||||
int network_init()
|
||||
|
@ -67,7 +64,11 @@ int network_init()
|
|||
dest_address.sin_family = AF_INET;
|
||||
dest_address.sin_addr.s_addr = inet_addr(DESTINATION_IP);
|
||||
dest_address.sin_port = htons( (unsigned short) UDP_PORT );
|
||||
|
||||
|
||||
spaceserver_address.sin_family = AF_INET;
|
||||
spaceserver_address.sin_addr.s_addr = inet_addr(SPACESERVER_IP);
|
||||
spaceserver_address.sin_port = htons( (unsigned short) SPACESERVER_PORT );
|
||||
|
||||
from.sin_family = AF_INET;
|
||||
//from.sin_addr.s_addr = htonl(ip_address);
|
||||
from.sin_port = htons( (unsigned short) UDP_PORT );
|
||||
|
@ -86,6 +87,22 @@ timeval network_send_ping(int handle) {
|
|||
return check;
|
||||
}
|
||||
|
||||
int notify_spaceserver(int handle, float x, float y, float z) {
|
||||
char data[100];
|
||||
sprintf(data, "%f,%f,%f", x, y, z);
|
||||
//std::cout << "sending: " << data << "\n";
|
||||
int packet_size = strlen(data);
|
||||
int sent_bytes = sendto( handle, (const char*)data, packet_size,
|
||||
0, (sockaddr*)&spaceserver_address, sizeof(sockaddr_in) );
|
||||
|
||||
if ( sent_bytes != packet_size )
|
||||
{
|
||||
printf( "failed to send to spaceserver: return value = %d\n", sent_bytes );
|
||||
return false;
|
||||
}
|
||||
return sent_bytes;
|
||||
}
|
||||
|
||||
int network_send(int handle, char * packet_data, int packet_size)
|
||||
{
|
||||
int sent_bytes = sendto( handle, (const char*)packet_data, packet_size,
|
||||
|
|
|
@ -16,11 +16,19 @@
|
|||
#include <sys/time.h>
|
||||
#include "util.h"
|
||||
|
||||
// Port to use for communicating UDP with other nearby agents
|
||||
const int MAX_PACKET_SIZE = 1500;
|
||||
const int UDP_PORT = 30001;
|
||||
const char DESTINATION_IP[] = "127.0.0.1";
|
||||
|
||||
// Address and port of spaceserver process to advertise other agents
|
||||
const char SPACESERVER_IP[] = "127.0.0.1";
|
||||
const int SPACESERVER_PORT = 40000;
|
||||
|
||||
int network_init();
|
||||
int network_send(int handle, char * packet_data, int packet_size);
|
||||
int network_receive(int handle, char * packet_data, int delay /*msecs*/);
|
||||
timeval network_send_ping(int handle);
|
||||
int notify_spaceserver(int handle, float x, float y, float z);
|
||||
|
||||
#endif
|
||||
|
|
470
tga.h
470
tga.h
|
@ -1,470 +0,0 @@
|
|||
#include <iostream>
|
||||
#include <fstream>
|
||||
#include <memory.h>
|
||||
|
||||
#define IMG_OK 0x1
|
||||
#define IMG_ERR_NO_FILE 0x2
|
||||
#define IMG_ERR_MEM_FAIL 0x4
|
||||
#define IMG_ERR_BAD_FORMAT 0x8
|
||||
#define IMG_ERR_UNSUPPORTED 0x40
|
||||
|
||||
class TGAImg
|
||||
{
|
||||
public:
|
||||
TGAImg();
|
||||
~TGAImg();
|
||||
int Load(char* szFilename);
|
||||
int GetBPP();
|
||||
int GetWidth();
|
||||
int GetHeight();
|
||||
unsigned char* GetImg(); // Return a pointer to image data
|
||||
unsigned char* GetPalette(); // Return a pointer to VGA palette
|
||||
|
||||
private:
|
||||
short int iWidth,iHeight,iBPP;
|
||||
unsigned long lImageSize;
|
||||
char bEnc;
|
||||
unsigned char *pImage, *pPalette, *pData;
|
||||
|
||||
// Internal workers
|
||||
int ReadHeader();
|
||||
int LoadRawData();
|
||||
int LoadTgaRLEData();
|
||||
int LoadTgaPalette();
|
||||
void BGRtoRGB();
|
||||
void FlipImg();
|
||||
};
|
||||
|
||||
|
||||
TGAImg::TGAImg()
|
||||
{
|
||||
pImage=pPalette=pData=NULL;
|
||||
iWidth=iHeight=iBPP=bEnc=0;
|
||||
lImageSize=0;
|
||||
}
|
||||
|
||||
|
||||
TGAImg::~TGAImg()
|
||||
{
|
||||
if(pImage)
|
||||
{
|
||||
delete [] pImage;
|
||||
pImage=NULL;
|
||||
}
|
||||
|
||||
if(pPalette)
|
||||
{
|
||||
delete [] pPalette;
|
||||
pPalette=NULL;
|
||||
}
|
||||
|
||||
if(pData)
|
||||
{
|
||||
delete [] pData;
|
||||
pData=NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::Load(char* szFilename)
|
||||
{
|
||||
using namespace std;
|
||||
ifstream fIn;
|
||||
unsigned long ulSize;
|
||||
int iRet;
|
||||
|
||||
// Clear out any existing image and palette
|
||||
if(pImage)
|
||||
{
|
||||
delete [] pImage;
|
||||
pImage=NULL;
|
||||
}
|
||||
|
||||
if(pPalette)
|
||||
{
|
||||
delete [] pPalette;
|
||||
pPalette=NULL;
|
||||
}
|
||||
|
||||
// Open the specified file
|
||||
fIn.open(szFilename,ios::binary);
|
||||
|
||||
if(fIn==NULL)
|
||||
return IMG_ERR_NO_FILE;
|
||||
|
||||
// Get file size
|
||||
fIn.seekg(0,ios_base::end);
|
||||
ulSize=fIn.tellg();
|
||||
fIn.seekg(0,ios_base::beg);
|
||||
|
||||
// Allocate some space
|
||||
// Check and clear pDat, just in case
|
||||
if(pData)
|
||||
delete [] pData;
|
||||
|
||||
pData=new unsigned char[ulSize];
|
||||
|
||||
if(pData==NULL)
|
||||
{
|
||||
fIn.close();
|
||||
return IMG_ERR_MEM_FAIL;
|
||||
}
|
||||
|
||||
// Read the file into memory
|
||||
fIn.read((char*)pData,ulSize);
|
||||
|
||||
fIn.close();
|
||||
|
||||
// Process the header
|
||||
iRet=ReadHeader();
|
||||
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
switch(bEnc)
|
||||
{
|
||||
case 1: // Raw Indexed
|
||||
{
|
||||
// Check filesize against header values
|
||||
if((lImageSize+18+pData[0]+768)>ulSize)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Double check image type field
|
||||
if(pData[1]!=1)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Load image data
|
||||
iRet=LoadRawData();
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
// Load palette
|
||||
iRet=LoadTgaPalette();
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case 2: // Raw RGB
|
||||
{
|
||||
// Check filesize against header values
|
||||
if((lImageSize+18+pData[0])>ulSize)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Double check image type field
|
||||
if(pData[1]!=0)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Load image data
|
||||
iRet=LoadRawData();
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
BGRtoRGB(); // Convert to RGB
|
||||
break;
|
||||
}
|
||||
|
||||
case 9: // RLE Indexed
|
||||
{
|
||||
// Double check image type field
|
||||
if(pData[1]!=1)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Load image data
|
||||
iRet=LoadTgaRLEData();
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
// Load palette
|
||||
iRet=LoadTgaPalette();
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case 10: // RLE RGB
|
||||
{
|
||||
// Double check image type field
|
||||
if(pData[1]!=0)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Load image data
|
||||
iRet=LoadTgaRLEData();
|
||||
if(iRet!=IMG_OK)
|
||||
return iRet;
|
||||
|
||||
BGRtoRGB(); // Convert to RGB
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
return IMG_ERR_UNSUPPORTED;
|
||||
}
|
||||
|
||||
// Check flip bit
|
||||
if((pData[17] & 0x20)==0)
|
||||
FlipImg();
|
||||
|
||||
// Release file memory
|
||||
delete [] pData;
|
||||
pData=NULL;
|
||||
|
||||
return IMG_OK;
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::ReadHeader() // Examine the header and populate our class attributes
|
||||
{
|
||||
short ColMapStart,ColMapLen;
|
||||
short x1,y1,x2,y2;
|
||||
|
||||
if(pData==NULL)
|
||||
return IMG_ERR_NO_FILE;
|
||||
|
||||
if(pData[1]>1) // 0 (RGB) and 1 (Indexed) are the only types we know about
|
||||
return IMG_ERR_UNSUPPORTED;
|
||||
|
||||
bEnc=pData[2]; // Encoding flag 1 = Raw indexed image
|
||||
// 2 = Raw RGB
|
||||
// 3 = Raw greyscale
|
||||
// 9 = RLE indexed
|
||||
// 10 = RLE RGB
|
||||
// 11 = RLE greyscale
|
||||
// 32 & 33 Other compression, indexed
|
||||
|
||||
if(bEnc>11) // We don't want 32 or 33
|
||||
return IMG_ERR_UNSUPPORTED;
|
||||
|
||||
|
||||
// Get palette info
|
||||
memcpy(&ColMapStart,&pData[3],2);
|
||||
memcpy(&ColMapLen,&pData[5],2);
|
||||
|
||||
// Reject indexed images if not a VGA palette (256 entries with 24 bits per entry)
|
||||
if(pData[1]==1) // Indexed
|
||||
{
|
||||
if(ColMapStart!=0 || ColMapLen!=256 || pData[7]!=24)
|
||||
return IMG_ERR_UNSUPPORTED;
|
||||
}
|
||||
|
||||
// Get image window and produce width & height values
|
||||
memcpy(&x1,&pData[8],2);
|
||||
memcpy(&y1,&pData[10],2);
|
||||
memcpy(&x2,&pData[12],2);
|
||||
memcpy(&y2,&pData[14],2);
|
||||
|
||||
iWidth=(x2-x1);
|
||||
iHeight=(y2-y1);
|
||||
|
||||
if(iWidth<1 || iHeight<1)
|
||||
return IMG_ERR_BAD_FORMAT;
|
||||
|
||||
// Bits per Pixel
|
||||
iBPP=pData[16];
|
||||
|
||||
// Check flip / interleave byte
|
||||
if(pData[17]>32) // Interleaved data
|
||||
return IMG_ERR_UNSUPPORTED;
|
||||
|
||||
// Calculate image size
|
||||
lImageSize=(iWidth * iHeight * (iBPP/8));
|
||||
|
||||
return IMG_OK;
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::LoadRawData() // Load uncompressed image data
|
||||
{
|
||||
short iOffset;
|
||||
|
||||
if(pImage) // Clear old data if present
|
||||
delete [] pImage;
|
||||
|
||||
pImage=new unsigned char[lImageSize];
|
||||
|
||||
if(pImage==NULL)
|
||||
return IMG_ERR_MEM_FAIL;
|
||||
|
||||
iOffset=pData[0]+18; // Add header to ident field size
|
||||
|
||||
if(pData[1]==1) // Indexed images
|
||||
iOffset+=768; // Add palette offset
|
||||
|
||||
memcpy(pImage,&pData[iOffset],lImageSize);
|
||||
|
||||
return IMG_OK;
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::LoadTgaRLEData() // Load RLE compressed image data
|
||||
{
|
||||
short iOffset,iPixelSize;
|
||||
unsigned char *pCur;
|
||||
unsigned long Index=0;
|
||||
unsigned char bLength,bLoop;
|
||||
|
||||
// Calculate offset to image data
|
||||
iOffset=pData[0]+18;
|
||||
|
||||
// Add palette offset for indexed images
|
||||
if(pData[1]==1)
|
||||
iOffset+=768;
|
||||
|
||||
// Get pixel size in bytes
|
||||
iPixelSize=iBPP/8;
|
||||
|
||||
// Set our pointer to the beginning of the image data
|
||||
pCur=&pData[iOffset];
|
||||
|
||||
// Allocate space for the image data
|
||||
if(pImage!=NULL)
|
||||
delete [] pImage;
|
||||
|
||||
pImage=new unsigned char[lImageSize];
|
||||
|
||||
if(pImage==NULL)
|
||||
return IMG_ERR_MEM_FAIL;
|
||||
|
||||
// Decode
|
||||
while(Index<lImageSize)
|
||||
{
|
||||
if(*pCur & 0x80) // Run length chunk (High bit = 1)
|
||||
{
|
||||
bLength=*pCur-127; // Get run length
|
||||
pCur++; // Move to pixel data
|
||||
|
||||
// Repeat the next pixel bLength times
|
||||
for(bLoop=0;bLoop!=bLength;++bLoop,Index+=iPixelSize)
|
||||
memcpy(&pImage[Index],pCur,iPixelSize);
|
||||
|
||||
pCur+=iPixelSize; // Move to the next descriptor chunk
|
||||
}
|
||||
else // Raw chunk
|
||||
{
|
||||
bLength=*pCur+1; // Get run length
|
||||
pCur++; // Move to pixel data
|
||||
|
||||
// Write the next bLength pixels directly
|
||||
for(bLoop=0;bLoop!=bLength;++bLoop,Index+=iPixelSize,pCur+=iPixelSize)
|
||||
memcpy(&pImage[Index],pCur,iPixelSize);
|
||||
}
|
||||
}
|
||||
|
||||
return IMG_OK;
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::LoadTgaPalette() // Load a 256 color palette
|
||||
{
|
||||
unsigned char bTemp;
|
||||
short iIndex,iPalPtr;
|
||||
|
||||
// Delete old palette if present
|
||||
if(pPalette)
|
||||
{
|
||||
delete [] pPalette;
|
||||
pPalette=NULL;
|
||||
}
|
||||
|
||||
// Create space for new palette
|
||||
pPalette=new unsigned char[768];
|
||||
|
||||
if(pPalette==NULL)
|
||||
return IMG_ERR_MEM_FAIL;
|
||||
|
||||
// VGA palette is the 768 bytes following the header
|
||||
memcpy(pPalette,&pData[pData[0]+18],768);
|
||||
|
||||
// Palette entries are BGR ordered so we have to convert to RGB
|
||||
for(iIndex=0,iPalPtr=0;iIndex!=256;++iIndex,iPalPtr+=3)
|
||||
{
|
||||
bTemp=pPalette[iPalPtr]; // Get Blue value
|
||||
pPalette[iPalPtr]=pPalette[iPalPtr+2]; // Copy Red to Blue
|
||||
pPalette[iPalPtr+2]=bTemp; // Replace Blue at the end
|
||||
}
|
||||
|
||||
return IMG_OK;
|
||||
}
|
||||
|
||||
|
||||
void TGAImg::BGRtoRGB() // Convert BGR to RGB (or back again)
|
||||
{
|
||||
unsigned long Index,nPixels;
|
||||
unsigned char *bCur;
|
||||
unsigned char bTemp;
|
||||
short iPixelSize;
|
||||
|
||||
// Set ptr to start of image
|
||||
bCur=pImage;
|
||||
|
||||
// Calc number of pixels
|
||||
nPixels=iWidth*iHeight;
|
||||
|
||||
// Get pixel size in bytes
|
||||
iPixelSize=iBPP/8;
|
||||
|
||||
for(Index=0;Index!=nPixels;Index++) // For each pixel
|
||||
{
|
||||
bTemp=*bCur; // Get Blue value
|
||||
*bCur=*(bCur+2); // Swap red value into first position
|
||||
*(bCur+2)=bTemp; // Write back blue to last position
|
||||
|
||||
bCur+=iPixelSize; // Jump to next pixel
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
void TGAImg::FlipImg() // Flips the image vertically (Why store images upside down?)
|
||||
{
|
||||
unsigned char bTemp;
|
||||
unsigned char *pLine1, *pLine2;
|
||||
int iLineLen,iIndex;
|
||||
|
||||
iLineLen=iWidth*(iBPP/8);
|
||||
pLine1=pImage;
|
||||
pLine2=&pImage[iLineLen * (iHeight - 1)];
|
||||
|
||||
for( ;pLine1<pLine2;pLine2-=(iLineLen*2))
|
||||
{
|
||||
for(iIndex=0;iIndex!=iLineLen;pLine1++,pLine2++,iIndex++)
|
||||
{
|
||||
bTemp=*pLine1;
|
||||
*pLine1=*pLine2;
|
||||
*pLine2=bTemp;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::GetBPP()
|
||||
{
|
||||
return iBPP;
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::GetWidth()
|
||||
{
|
||||
return iWidth;
|
||||
}
|
||||
|
||||
|
||||
int TGAImg::GetHeight()
|
||||
{
|
||||
return iHeight;
|
||||
}
|
||||
|
||||
|
||||
unsigned char* TGAImg::GetImg()
|
||||
{
|
||||
return pImage;
|
||||
}
|
||||
|
||||
|
||||
unsigned char* TGAImg::GetPalette()
|
||||
{
|
||||
return pPalette;
|
||||
}
|
71
util.cpp
71
util.cpp
|
@ -15,11 +15,75 @@
|
|||
#include "world.h"
|
||||
#include "glm/glm.hpp"
|
||||
|
||||
|
||||
float randFloat () {
|
||||
return (rand()%10000)/10000.f;
|
||||
}
|
||||
|
||||
void makeCubes(float location[3], float scale, int * index,
|
||||
float * cubes_position, float * cubes_scale, float * cubes_color) {
|
||||
int i;
|
||||
float spot[3];
|
||||
//std::cout << "loc: " << location[0] << ","
|
||||
//<< location[1] << "," << location[2] << "\n";
|
||||
if ((*index >= MAX_CUBES) || (scale < SMALLEST_CUBE)) return;
|
||||
if (randFloat() < 0.5) {
|
||||
// Make a cube
|
||||
for (i = 0; i < 3; i++) cubes_position[*index*3 + i] = location[i];
|
||||
cubes_scale[*index] = scale;
|
||||
cubes_color[*index*3] = randFloat();
|
||||
cubes_color[*index*3 + 1] = randFloat();
|
||||
cubes_color[*index*3 + 2] = randFloat();
|
||||
*index += 1;
|
||||
//std::cout << "Quad made at scale " << scale << "\n";
|
||||
} else {
|
||||
for (i = 0; i < 8; i++) {
|
||||
spot[0] = location[0] + (i%2)*scale/2.0;
|
||||
spot[1] = location[1] + ((i/2)%2)*scale/2.0;
|
||||
spot[2] = location[2] + ((i/4)%2)*scale/2.0;
|
||||
//std::cout << spot[0] << "," << spot[1] << "," << spot[2] << "\n";
|
||||
makeCubes(spot, scale/2.0, index, cubes_position, cubes_scale, cubes_color);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void render_vector(glm::vec3 * vec)
|
||||
{
|
||||
// Show edge of world
|
||||
glDisable(GL_LIGHTING);
|
||||
glColor4f(1.0, 1.0, 1.0, 1.0);
|
||||
glLineWidth(1.0);
|
||||
glBegin(GL_LINES);
|
||||
// Draw axes
|
||||
glColor3f(1,0,0);
|
||||
glVertex3f(-1,0,0);
|
||||
glVertex3f(1,0,0);
|
||||
glColor3f(0,1,0);
|
||||
glVertex3f(0,-1,0);
|
||||
glVertex3f(0, 1, 0);
|
||||
glColor3f(0,0,1);
|
||||
glVertex3f(0,0,-1);
|
||||
glVertex3f(0, 0, 1);
|
||||
// Draw vector
|
||||
glColor3f(1,1,1);
|
||||
glVertex3f(0,0,0);
|
||||
glVertex3f(vec->x, vec->y, vec->z);
|
||||
// Draw marker dots for magnitude
|
||||
glEnd();
|
||||
float particle_attenuation_quadratic[] = { 0.0f, 0.0f, 2.0f }; // larger Z = smaller particles
|
||||
glPointParameterfvARB( GL_POINT_DISTANCE_ATTENUATION_ARB, particle_attenuation_quadratic );
|
||||
glEnable(GL_POINT_SMOOTH);
|
||||
glPointSize(10.0);
|
||||
glBegin(GL_POINTS);
|
||||
glColor3f(1,0,0);
|
||||
glVertex3f(vec->x,0,0);
|
||||
glColor3f(0,1,0);
|
||||
glVertex3f(0,vec->y,0);
|
||||
glColor3f(0,0,1);
|
||||
glVertex3f(0,0,vec->z);
|
||||
glEnd();
|
||||
|
||||
}
|
||||
|
||||
void render_world_box()
|
||||
{
|
||||
// Show edge of world
|
||||
|
@ -39,6 +103,11 @@ void render_world_box()
|
|||
glEnd();
|
||||
}
|
||||
|
||||
void outstring(char * string, int length) {
|
||||
char out[length];
|
||||
memcpy(out, string, length);
|
||||
std::cout << out << "\n";
|
||||
}
|
||||
|
||||
double diffclock(timeval clock1,timeval clock2)
|
||||
{
|
||||
|
|
6
util.h
6
util.h
|
@ -8,14 +8,20 @@
|
|||
|
||||
#ifndef interface_util_h
|
||||
#define interface_util_h
|
||||
|
||||
#include "glm/glm.hpp"
|
||||
|
||||
void outstring(char * string, int length);
|
||||
float randFloat();
|
||||
void render_world_box();
|
||||
void render_vector(glm::vec3 * vec);
|
||||
void drawtext(int x, int y, float scale, float rotate, float thick, int mono, char *string,
|
||||
float r=1.0, float g=1.0, float b=1.0);
|
||||
void drawvec3(int x, int y, float scale, float rotate, float thick, int mono, glm::vec3 vec,
|
||||
float r=1.0, float g=1.0, float b=1.0);
|
||||
double diffclock(timeval clock1,timeval clock2);
|
||||
|
||||
void makeCubes(float location[3], float scale, int * index,
|
||||
float * cubes_position, float * cubes_scale, float * cubes_color);
|
||||
|
||||
#endif
|
||||
|
|
4
world.h
4
world.h
|
@ -6,7 +6,7 @@
|
|||
// Copyright (c) 2012 __MyCompanyName__. All rights reserved.
|
||||
//
|
||||
|
||||
// Simulation happens in positive cube with edge of size WORLD_SIZE
|
||||
// Simulation happens in positive cube with edge of size WORLD_SIZE
|
||||
|
||||
#ifndef interface_world_h
|
||||
#define interface_world_h
|
||||
|
@ -14,5 +14,7 @@
|
|||
const float WORLD_SIZE = 10.0;
|
||||
#define PI 3.14159265
|
||||
|
||||
#define MAX_CUBES 2000
|
||||
#define SMALLEST_CUBE 0.01
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Reference in a new issue