rev |
line source |
nuclear@5
|
1 #include <stdio.h>
|
nuclear@5
|
2 #include <string.h>
|
nuclear@5
|
3 #include <errno.h>
|
nuclear@5
|
4 #include <windows.h>
|
nuclear@5
|
5 #include <shlobj.h>
|
nuclear@5
|
6 #include "max.h"
|
nuclear@5
|
7 #include "impexp.h" // SceneExport
|
nuclear@5
|
8 #include "iparamb2.h" // ClassDesc2
|
nuclear@5
|
9 #include "plugapi.h"
|
nuclear@5
|
10 #include "IGame.h"
|
nuclear@5
|
11 #include "IGameExport.h"
|
nuclear@5
|
12 #include "IConversionmanager.h"
|
nuclear@10
|
13 #include "config.h"
|
nuclear@5
|
14
|
nuclear@5
|
15
|
nuclear@5
|
16 #pragma comment (lib, "core.lib")
|
nuclear@5
|
17 #pragma comment (lib, "geom.lib")
|
nuclear@5
|
18 #pragma comment (lib, "gfx.lib")
|
nuclear@5
|
19 #pragma comment (lib, "mesh.lib")
|
nuclear@5
|
20 #pragma comment (lib, "maxutil.lib")
|
nuclear@5
|
21 #pragma comment (lib, "maxscrpt.lib")
|
nuclear@5
|
22 #pragma comment (lib, "paramblk2.lib")
|
nuclear@5
|
23 #pragma comment (lib, "msxml2.lib")
|
nuclear@5
|
24 #pragma comment (lib, "igame.lib")
|
nuclear@5
|
25 #pragma comment (lib, "comctl32.lib")
|
nuclear@5
|
26
|
nuclear@5
|
27
|
nuclear@10
|
28 #define VERSION(major, minor) \
|
nuclear@10
|
29 ((major) * 100 + ((minor) < 10 ? (minor) * 10 : (minor)))
|
nuclear@10
|
30
|
nuclear@5
|
31 static FILE *logfile;
|
nuclear@5
|
32 static HINSTANCE hinst;
|
nuclear@5
|
33
|
nuclear@5
|
34 class GoatExporter : public SceneExport {
|
nuclear@5
|
35 public:
|
nuclear@5
|
36 IGameScene *igame;
|
nuclear@5
|
37
|
nuclear@5
|
38 int ExtCount();
|
nuclear@5
|
39 const TCHAR *Ext(int n);
|
nuclear@5
|
40 const TCHAR *LongDesc();
|
nuclear@5
|
41 const TCHAR *ShortDesc();
|
nuclear@5
|
42 const TCHAR *AuthorName();
|
nuclear@5
|
43 const TCHAR *CopyrightMessage();
|
nuclear@5
|
44 const TCHAR *OtherMessage1();
|
nuclear@5
|
45 const TCHAR *OtherMessage2();
|
nuclear@5
|
46 unsigned int Version();
|
nuclear@5
|
47 void ShowAbout(HWND win);
|
nuclear@5
|
48
|
nuclear@5
|
49 int DoExport(const MCHAR *name, ExpInterface *eiface, Interface *iface, BOOL silent = FALSE, DWORD opt = 0);
|
nuclear@5
|
50
|
nuclear@5
|
51 bool export_materials(FILE *fp);
|
nuclear@5
|
52 };
|
nuclear@5
|
53
|
nuclear@5
|
54
|
nuclear@5
|
55 int GoatExporter::ExtCount()
|
nuclear@5
|
56 {
|
nuclear@5
|
57 return 1;
|
nuclear@5
|
58 }
|
nuclear@5
|
59
|
nuclear@5
|
60 const TCHAR *GoatExporter::Ext(int n)
|
nuclear@5
|
61 {
|
nuclear@5
|
62 return L"txt";
|
nuclear@5
|
63 }
|
nuclear@5
|
64
|
nuclear@5
|
65 const TCHAR *GoatExporter::LongDesc()
|
nuclear@5
|
66 {
|
nuclear@5
|
67 return L"Goat3D scene file";
|
nuclear@5
|
68 }
|
nuclear@5
|
69
|
nuclear@5
|
70 const TCHAR *GoatExporter::ShortDesc()
|
nuclear@5
|
71 {
|
nuclear@5
|
72 return L"Goat3D";
|
nuclear@5
|
73 }
|
nuclear@5
|
74
|
nuclear@5
|
75 const TCHAR *GoatExporter::AuthorName()
|
nuclear@5
|
76 {
|
nuclear@5
|
77 return L"John Tsiombikas";
|
nuclear@5
|
78 }
|
nuclear@5
|
79
|
nuclear@5
|
80 const TCHAR *GoatExporter::CopyrightMessage()
|
nuclear@5
|
81 {
|
nuclear@5
|
82 return L"Copyright 2013 (C) John Tsiombikas - GNU General Public License v3, see COPYING for details.";
|
nuclear@5
|
83 }
|
nuclear@5
|
84
|
nuclear@5
|
85 const TCHAR *GoatExporter::OtherMessage1()
|
nuclear@5
|
86 {
|
nuclear@5
|
87 return L"other1";
|
nuclear@5
|
88 }
|
nuclear@5
|
89
|
nuclear@5
|
90 const TCHAR *GoatExporter::OtherMessage2()
|
nuclear@5
|
91 {
|
nuclear@5
|
92 return L"other2";
|
nuclear@5
|
93 }
|
nuclear@5
|
94
|
nuclear@5
|
95 unsigned int GoatExporter::Version()
|
nuclear@5
|
96 {
|
nuclear@10
|
97 return VERSION(VER_MAJOR, VER_MINOR);
|
nuclear@5
|
98 }
|
nuclear@5
|
99
|
nuclear@5
|
100 void GoatExporter::ShowAbout(HWND win)
|
nuclear@5
|
101 {
|
nuclear@5
|
102 MessageBoxA(win, "Goat3D exporter plugin", "About this plugin", 0);
|
nuclear@5
|
103 }
|
nuclear@5
|
104
|
nuclear@5
|
105 int GoatExporter::DoExport(const MCHAR *name, ExpInterface *eiface, Interface *iface,
|
nuclear@5
|
106 BOOL non_interactive, DWORD opt)
|
nuclear@5
|
107 {
|
nuclear@5
|
108 char fname[512];
|
nuclear@5
|
109 wcstombs(fname, name, sizeof fname - 1);
|
nuclear@5
|
110
|
nuclear@5
|
111 FILE *fp = fopen(fname, "wb");
|
nuclear@5
|
112 if(!fp) {
|
nuclear@5
|
113 fprintf(logfile, "failed to open %s for writting: %s", fname, strerror(errno));
|
nuclear@5
|
114 return IMPEXP_FAIL;
|
nuclear@5
|
115 }
|
nuclear@5
|
116
|
nuclear@5
|
117 if(!(igame = GetIGameInterface())) {
|
nuclear@5
|
118 fprintf(logfile, "failed to get the igame interface\n");
|
nuclear@5
|
119 fclose(fp);
|
nuclear@5
|
120 return IMPEXP_FAIL;
|
nuclear@5
|
121 }
|
nuclear@5
|
122 IGameConversionManager *cm = GetConversionManager();
|
nuclear@5
|
123 cm->SetCoordSystem(IGameConversionManager::IGAME_OGL);
|
nuclear@5
|
124 igame->InitialiseIGame();
|
nuclear@5
|
125 igame->SetStaticFrame(0);
|
nuclear@5
|
126
|
nuclear@5
|
127 export_materials(fp);
|
nuclear@5
|
128
|
nuclear@5
|
129 fclose(fp);
|
nuclear@5
|
130
|
nuclear@5
|
131 return IMPEXP_SUCCESS;
|
nuclear@5
|
132 }
|
nuclear@5
|
133
|
nuclear@5
|
134 bool GoatExporter::export_materials(FILE *fp)
|
nuclear@5
|
135 {
|
nuclear@5
|
136 IGameProperty *prop;
|
nuclear@5
|
137
|
nuclear@5
|
138 int num_mtl = igame->GetRootMaterialCount();
|
nuclear@5
|
139 fprintf(fp, "number of materials: %d\n", num_mtl);
|
nuclear@5
|
140
|
nuclear@5
|
141 for(int i=0; i<num_mtl; i++) {
|
nuclear@5
|
142 IGameMaterial *mtl = igame->GetRootMaterial(i);
|
nuclear@5
|
143 if(mtl) {
|
nuclear@5
|
144 Point3 diffuse(1, 1, 1);
|
nuclear@5
|
145 Point3 specular(0, 0, 0);
|
nuclear@5
|
146 float shin = 1.0, sstr = 1.0;
|
nuclear@5
|
147 char name[512] = "unnamed";
|
nuclear@5
|
148
|
nuclear@5
|
149 const MCHAR *wname = mtl->GetMaterialName();
|
nuclear@5
|
150 if(wname) {
|
nuclear@5
|
151 wcstombs(name, wname, sizeof name - 1);
|
nuclear@5
|
152 }
|
nuclear@5
|
153
|
nuclear@5
|
154 if((prop = mtl->GetDiffuseData())) {
|
nuclear@5
|
155 prop->GetPropertyValue(diffuse);
|
nuclear@5
|
156 }
|
nuclear@5
|
157 if((prop = mtl->GetSpecularData())) {
|
nuclear@5
|
158 prop->GetPropertyValue(specular);
|
nuclear@5
|
159 }
|
nuclear@5
|
160 if((prop = mtl->GetSpecularLevelData())) {
|
nuclear@5
|
161 prop->GetPropertyValue(sstr);
|
nuclear@5
|
162 }
|
nuclear@5
|
163 if((prop = mtl->GetGlossinessData())) {
|
nuclear@5
|
164 prop->GetPropertyValue(shin);
|
nuclear@5
|
165 }
|
nuclear@5
|
166
|
nuclear@5
|
167 fprintf(fp, "Material %d (%s):\n", i, name);
|
nuclear@5
|
168 fprintf(fp, " diffuse: %f %f %f\n", diffuse[0], diffuse[1], diffuse[2]);
|
nuclear@5
|
169 fprintf(fp, " specular: %f %f %f\n", specular[0] * sstr, specular[1] * sstr, specular[2] * sstr);
|
nuclear@5
|
170 fprintf(fp, " shininess: %f\n", shin * 100.0);
|
nuclear@5
|
171
|
nuclear@5
|
172 for(int j=0; j<mtl->GetNumberOfTextureMaps(); j++) {
|
nuclear@5
|
173 IGameTextureMap *tex = mtl->GetIGameTextureMap(j);
|
nuclear@5
|
174 const MCHAR *wfname = tex->GetBitmapFileName();
|
nuclear@5
|
175 if(wfname) {
|
nuclear@5
|
176 char fname[512];
|
nuclear@5
|
177 wcstombs(fname, wfname, sizeof fname - 1);
|
nuclear@5
|
178 fprintf(fp, " texture%d: %s\n", j, fname);
|
nuclear@5
|
179 }
|
nuclear@5
|
180 }
|
nuclear@5
|
181 }
|
nuclear@5
|
182 }
|
nuclear@5
|
183
|
nuclear@5
|
184 return true;
|
nuclear@5
|
185 }
|
nuclear@5
|
186
|
nuclear@5
|
187 // ------------------------------------------
|
nuclear@5
|
188
|
nuclear@5
|
189 class GoatClassDesc : public ClassDesc2 {
|
nuclear@5
|
190 public:
|
nuclear@5
|
191 int IsPublic() { return TRUE; }
|
nuclear@5
|
192 void *Create(BOOL loading = FALSE) { return new GoatExporter; }
|
nuclear@5
|
193 const TCHAR *ClassName() { return L"GoatExporter"; }
|
nuclear@5
|
194 SClass_ID SuperClassID() { return SCENE_EXPORT_CLASS_ID; }
|
nuclear@5
|
195 Class_ID ClassID() { return Class_ID(0x77050f0d, 0x7d4c5ab5); }
|
nuclear@5
|
196 const TCHAR *Category() { return L"Mutant Stargoat"; }
|
nuclear@5
|
197
|
nuclear@5
|
198 const TCHAR *InternalName() { return L"GoatExporter"; }
|
nuclear@5
|
199 HINSTANCE HInstance() { return hinst; }
|
nuclear@5
|
200 };
|
nuclear@5
|
201
|
nuclear@5
|
202 static GoatClassDesc class_desc;
|
nuclear@5
|
203
|
nuclear@5
|
204 BOOL WINAPI DllMain(HINSTANCE inst_handle, ULONG reason, void *reserved)
|
nuclear@5
|
205 {
|
nuclear@5
|
206 if(reason == DLL_PROCESS_ATTACH) {
|
nuclear@5
|
207 hinst = inst_handle;
|
nuclear@5
|
208 DisableThreadLibraryCalls(hinst);
|
nuclear@5
|
209 }
|
nuclear@5
|
210 return TRUE;
|
nuclear@5
|
211 }
|
nuclear@5
|
212
|
nuclear@5
|
213 extern "C" {
|
nuclear@5
|
214
|
nuclear@5
|
215 __declspec(dllexport) const TCHAR *LibDescription()
|
nuclear@5
|
216 {
|
nuclear@5
|
217 return L"test exporter";
|
nuclear@5
|
218 }
|
nuclear@5
|
219
|
nuclear@5
|
220 __declspec(dllexport) int LibNumberClasses()
|
nuclear@5
|
221 {
|
nuclear@5
|
222 return 1;
|
nuclear@5
|
223 }
|
nuclear@5
|
224
|
nuclear@5
|
225 __declspec(dllexport) ClassDesc *LibClassDesc(int i)
|
nuclear@5
|
226 {
|
nuclear@5
|
227 return i == 0 ? &class_desc : 0;
|
nuclear@5
|
228 }
|
nuclear@5
|
229
|
nuclear@5
|
230 __declspec(dllexport) ULONG LibVersion()
|
nuclear@5
|
231 {
|
nuclear@5
|
232 return Get3DSMAXVersion();
|
nuclear@5
|
233 }
|
nuclear@5
|
234
|
nuclear@5
|
235 __declspec(dllexport) int LibInitialize()
|
nuclear@5
|
236 {
|
nuclear@5
|
237 static char path[1024];
|
nuclear@5
|
238
|
nuclear@5
|
239 SHGetFolderPathA(0, CSIDL_PERSONAL, 0, 0, path);
|
nuclear@5
|
240 strcat(path, "/testexp.log");
|
nuclear@5
|
241
|
nuclear@5
|
242 if((logfile = fopen(path, "w"))) {
|
nuclear@5
|
243 setvbuf(logfile, 0, _IONBF, 0);
|
nuclear@5
|
244 }
|
nuclear@5
|
245 return TRUE;
|
nuclear@5
|
246 }
|
nuclear@5
|
247
|
nuclear@5
|
248 __declspec(dllexport) int LibShutdown()
|
nuclear@5
|
249 {
|
nuclear@5
|
250 if(logfile) {
|
nuclear@5
|
251 fclose(logfile);
|
nuclear@5
|
252 logfile = 0;
|
nuclear@5
|
253 }
|
nuclear@5
|
254 return TRUE;
|
nuclear@5
|
255 }
|
nuclear@5
|
256
|
nuclear@5
|
257 } // extern "C" |