1/*
2 * Copyright 2008, Haiku Inc. All rights reserved.
3 * Distributed under the terms of the MIT License.
4 *
5 * Authors:
6 * 		Alexandre Deckner <alex@zappotek.com>
7 */
8
9#include "StaticMesh.h"
10
11#include <Application.h>
12#include <Resources.h>
13#include <Roster.h>
14#include <File.h>
15#include <String.h>
16
17#include <stdlib.h>
18#include <stdio.h>
19
20StaticMesh::StaticMesh(const char* name)
21	:
22	fFaces(NULL),
23	fFaceCount(0)
24{
25	// TODO : move that in a utility class
26	//BString fileName;
27	//fileName << "data/" << name << ".hk3d";
28	//_LoadText(fileName);
29
30	//fileName << ".bin";
31	//_WriteBinary(fileName);
32
33	_ReadResource(name);
34}
35
36
37StaticMesh::~StaticMesh()
38{
39	delete [] fFaces;
40}
41
42
43void
44StaticMesh::_ReadText(const char* fileName)
45{
46	FILE* f = fopen(fileName, "r");
47	if (f == NULL) {
48		printf("Mesh::_ReadText, error accessing %s\n", fileName);
49		return;
50	}
51
52	fscanf(f, "%" B_PRIu32, &fFaceCount);
53	fFaces = new Face[fFaceCount];
54
55	for (uint32 i = 0; i < fFaceCount; i++) {
56
57		uint32 vertexCount = 0;
58		fscanf(f, "%" B_PRIu32, &vertexCount);
59		fFaces[i].vertexCount = vertexCount;
60
61		for (uint32 vi = 0; vi < vertexCount; vi++) {
62			float x, y, z, u, v;
63			fscanf(f, "%f %f %f %f %f",	&x,	&y,	&z,	&v,	&u);
64			fFaces[i].v[vi].p.setValue(x, y, z);
65			fFaces[i].v[vi].u = v;
66			fFaces[i].v[vi].v = 1.0 - u;
67		}
68	}
69
70	fclose(f);
71	printf("Mesh::_ReadText, loaded %s (%" B_PRIu32 " faces)\n",
72		fileName, fFaceCount);
73}
74
75
76void
77StaticMesh::_WriteBinary(const char* fileName)
78{
79	BFile file(fileName, B_WRITE_ONLY | B_CREATE_FILE | B_ERASE_FILE);
80
81	if (file.InitCheck() != B_OK) {
82		printf("Mesh::_WriteBinary, error accessing %s\n", fileName);
83		return;
84	}
85
86	file.Write(&fFaceCount, sizeof(uint32));
87	for (uint32 i = 0; i < fFaceCount; i++) {
88		file.Write(&fFaces[i].vertexCount, sizeof(uint16));
89		for (uint32 vi = 0; vi < fFaces[i].vertexCount; vi++) {
90			file.Write(&fFaces[i].v[vi], sizeof(Vertex));
91		}
92	}
93	printf("Mesh::_WriteBinary, wrote %s (%" B_PRIu32 " faces)\n",
94		fileName, fFaceCount);
95}
96
97
98void
99StaticMesh::_ReadBinary(const char* fileName)
100{
101	BFile file(fileName, B_READ_ONLY);
102
103	if (file.InitCheck() != B_OK) {
104		printf("Mesh::_ReadBinary, error accessing %s\n", fileName);
105		return;
106	}
107
108	file.Read(&fFaceCount, sizeof(uint32));
109	fFaces = new Face[fFaceCount];
110	for (uint32 i = 0; i < fFaceCount; i++) {
111		file.Read(&fFaces[i].vertexCount, sizeof(uint16));
112		for (uint32 vi = 0; vi < fFaces[i].vertexCount; vi++) {
113			file.Read(&fFaces[i].v[vi], sizeof(Vertex));
114		}
115	}
116	printf("Mesh::_ReadBinary, loaded %s (%" B_PRIu32 " faces)\n",
117		fileName, fFaceCount);
118}
119
120
121void
122StaticMesh::_ReadResource(const char* resourceName)
123{
124	// TODO: factorize with _ReadBinary
125	app_info info;
126	be_app->GetAppInfo(&info);
127	BFile file(&info.ref, B_READ_ONLY);
128
129	BResources res;
130	if (res.SetTo(&file) != B_OK) {
131		printf("Mesh::_ReadResource, error accessing resources data\n");
132		return;
133	}
134
135	size_t size;
136	const void* data = res.LoadResource(B_RAW_TYPE, resourceName, &size);
137	if (data == NULL) {
138		printf("Mesh::_ReadResource, can't access resource %s\n", resourceName);
139		return;
140	}
141
142	BMemoryIO memoryIO(data, size);
143
144	memoryIO.Read(&fFaceCount, sizeof(uint32));
145	fFaces = new Face[fFaceCount];
146	for (uint32 i = 0; i < fFaceCount; i++) {
147		memoryIO.Read(&fFaces[i].vertexCount, sizeof(uint16));
148		for (uint32 vi = 0; vi < fFaces[i].vertexCount; vi++) {
149			memoryIO.Read(&fFaces[i].v[vi], sizeof(Vertex));
150		}
151	}
152	printf("Mesh::_ReadResource, loaded %s (%" B_PRIu32 " faces)\n",
153		resourceName, fFaceCount);
154}
155
156
157Face&
158StaticMesh::GetFace(uint32 index) const
159{
160	return fFaces[index];
161}
162
163
164uint32
165StaticMesh::FaceCount() const
166{
167	return fFaceCount;
168}
169