nuclear@58: #include nuclear@58: #include nuclear@58: #include nuclear@58: #include nuclear@58: #include nuclear@58: #include nuclear@58: #include nuclear@58: #include "max.h" nuclear@58: #include "impexp.h" // SceneExport nuclear@58: #include "iparamb2.h" // ClassDesc2 nuclear@58: #include "plugapi.h" nuclear@58: #include "IGame.h" nuclear@58: #include "IGameExport.h" nuclear@58: #include "IConversionmanager.h" nuclear@58: nuclear@58: nuclear@58: #pragma comment (lib, "core.lib") nuclear@58: #pragma comment (lib, "geom.lib") nuclear@58: #pragma comment (lib, "gfx.lib") nuclear@58: #pragma comment (lib, "mesh.lib") nuclear@58: #pragma comment (lib, "maxutil.lib") nuclear@58: #pragma comment (lib, "maxscrpt.lib") nuclear@58: #pragma comment (lib, "paramblk2.lib") nuclear@58: #pragma comment (lib, "msxml2.lib") nuclear@58: #pragma comment (lib, "igame.lib") nuclear@58: #pragma comment (lib, "comctl32.lib") nuclear@58: nuclear@58: nuclear@58: #define VER_MAJOR 1 nuclear@58: #define VER_MINOR 0 nuclear@58: #define VERSION(major, minor) \ nuclear@58: ((major) * 100 + ((minor) < 10 ? (minor) * 10 : (minor))) nuclear@58: nuclear@58: typedef int (*PluginInitFunc)(); nuclear@58: typedef int (*PluginShutdownFunc)(); nuclear@58: typedef ClassDesc *(*PluginClassDescFunc)(int); nuclear@58: nuclear@58: static FILE *logfile; nuclear@58: static HINSTANCE hinst; nuclear@58: nuclear@58: class GoatExporterStub : public SceneExport { nuclear@58: private: nuclear@58: nuclear@58: public: nuclear@58: IGameScene *igame; nuclear@58: nuclear@58: int ExtCount(); nuclear@58: const TCHAR *Ext(int n); nuclear@58: const TCHAR *LongDesc(); nuclear@58: const TCHAR *ShortDesc(); nuclear@58: const TCHAR *AuthorName(); nuclear@58: const TCHAR *CopyrightMessage(); nuclear@58: const TCHAR *OtherMessage1(); nuclear@58: const TCHAR *OtherMessage2(); nuclear@58: unsigned int Version(); nuclear@58: void ShowAbout(HWND win); nuclear@58: nuclear@58: int DoExport(const MCHAR *name, ExpInterface *eiface, Interface *iface, BOOL silent = FALSE, DWORD opt = 0); nuclear@58: }; nuclear@58: nuclear@58: nuclear@58: int GoatExporterStub::ExtCount() nuclear@58: { nuclear@58: return 1; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::Ext(int n) nuclear@58: { nuclear@58: return L"xml"; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::LongDesc() nuclear@58: { nuclear@58: return L"Goat3D scene file"; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::ShortDesc() nuclear@58: { nuclear@58: return L"Goat3D"; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::AuthorName() nuclear@58: { nuclear@58: return L"John Tsiombikas"; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::CopyrightMessage() nuclear@58: { nuclear@58: return L"Copyright 2013 (C) John Tsiombikas - GNU General Public License v3, see COPYING for details."; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::OtherMessage1() nuclear@58: { nuclear@58: return L"other1"; nuclear@58: } nuclear@58: nuclear@58: const TCHAR *GoatExporterStub::OtherMessage2() nuclear@58: { nuclear@58: return L"other2"; nuclear@58: } nuclear@58: nuclear@58: unsigned int GoatExporterStub::Version() nuclear@58: { nuclear@58: return VERSION(VER_MAJOR, VER_MINOR); nuclear@58: } nuclear@58: nuclear@58: void GoatExporterStub::ShowAbout(HWND win) nuclear@58: { nuclear@58: MessageBoxA(win, "Goat3D exporter stub", "About this plugin", 0); nuclear@58: } nuclear@58: nuclear@58: static const char *find_dll_dir() nuclear@58: { nuclear@58: static char path[MAX_PATH]; nuclear@58: nuclear@58: HMODULE dll; nuclear@58: if(!GetModuleHandleExA(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT, nuclear@58: (LPCSTR)find_dll_dir, &dll)) { nuclear@58: return 0; nuclear@58: } nuclear@58: GetModuleFileNameA(dll, path, sizeof path); nuclear@58: nuclear@58: char *last_slash = strrchr(path, '\\'); nuclear@58: if(last_slash && last_slash[1]) { nuclear@58: *last_slash = 0; nuclear@58: } nuclear@58: nuclear@58: return path; nuclear@58: } nuclear@58: nuclear@58: /* TODO: open a dialog, let the user select goat3d or goat3danim, then load the correct dll nuclear@58: */ nuclear@58: int GoatExporterStub::DoExport(const MCHAR *name, ExpInterface *eiface, Interface *iface, nuclear@58: BOOL non_interactive, DWORD opt) nuclear@58: { nuclear@58: const char *dll_fname = "maxgoat.dll"; nuclear@58: char *dll_path; nuclear@58: HMODULE dll = 0; nuclear@58: PluginInitFunc init; nuclear@58: PluginShutdownFunc shutdown; nuclear@58: PluginClassDescFunc get_class_desc; nuclear@58: ClassDesc *desc; nuclear@58: SceneExport *ex; nuclear@58: int result = IMPEXP_FAIL; nuclear@58: nuclear@58: const char *plugdir = find_dll_dir(); nuclear@58: if(plugdir) { nuclear@58: dll_path = new char[strlen(dll_fname) + strlen(plugdir) + 2]; nuclear@58: sprintf(dll_path, "%s\\%s", plugdir, dll_fname); nuclear@58: } else { nuclear@58: dll_path = new char[strlen(dll_fname) + 1]; nuclear@58: strcpy(dll_path, dll_fname); nuclear@58: } nuclear@58: nuclear@58: if(!(dll = LoadLibraryA(dll_path))) { nuclear@58: fprintf(logfile, "failed to load exporter: %s\n", dll_path); nuclear@58: goto done; nuclear@58: } nuclear@58: nuclear@58: if(!(get_class_desc = (PluginClassDescFunc)GetProcAddress(dll, "LibClassDesc"))) { nuclear@58: fprintf(logfile, "maxgoat.dll is invalid (no LibClassDesc function)\n"); nuclear@58: goto done; nuclear@58: } nuclear@58: nuclear@58: // first initialize the library nuclear@58: if((init = (PluginInitFunc)GetProcAddress(dll, "LibInitialize"))) { nuclear@58: if(!init()) { nuclear@58: fprintf(logfile, "exporter initialization failed!\n"); nuclear@58: goto done; nuclear@58: } nuclear@58: } nuclear@58: nuclear@58: // TODO: pass 1 for anim nuclear@58: if(!(desc = get_class_desc(0))) { nuclear@58: fprintf(logfile, "failed to get the class descriptor\n"); nuclear@58: goto done; nuclear@58: } nuclear@58: nuclear@58: if(!(ex = (SceneExport*)desc->Create())) { nuclear@58: fprintf(logfile, "failed to create exporter class instance\n"); nuclear@58: goto done; nuclear@58: } nuclear@58: nuclear@58: result = ex->DoExport(name, eiface, iface); nuclear@58: delete ex; nuclear@58: nuclear@58: if((shutdown = (PluginShutdownFunc)GetProcAddress(dll, "LibShutdown"))) { nuclear@58: shutdown(); nuclear@58: } nuclear@58: nuclear@58: done: nuclear@58: delete [] dll_path; nuclear@58: if(dll) { nuclear@58: FreeLibrary(dll); nuclear@58: } nuclear@58: return result; nuclear@58: } nuclear@58: nuclear@58: nuclear@58: // ------------------------------------------ nuclear@58: nuclear@58: class GoatClassDesc : public ClassDesc2 { nuclear@58: public: nuclear@58: int IsPublic() { return TRUE; } nuclear@58: void *Create(BOOL loading = FALSE) { return new GoatExporterStub; } nuclear@58: const TCHAR *ClassName() { return L"GoatExporterStub"; } nuclear@58: SClass_ID SuperClassID() { return SCENE_EXPORT_CLASS_ID; } nuclear@58: Class_ID ClassID() { return Class_ID(0x2e4e6311, 0x2b154d91); } nuclear@58: const TCHAR *Category() { return L"Mutant Stargoat"; } nuclear@58: nuclear@58: const TCHAR *InternalName() { return L"GoatExporterStub"; } nuclear@58: HINSTANCE HInstance() { return hinst; } nuclear@58: }; nuclear@58: nuclear@58: static GoatClassDesc class_desc; nuclear@58: nuclear@58: BOOL WINAPI DllMain(HINSTANCE inst_handle, ULONG reason, void *reserved) nuclear@58: { nuclear@58: if(reason == DLL_PROCESS_ATTACH) { nuclear@58: hinst = inst_handle; nuclear@58: DisableThreadLibraryCalls(hinst); nuclear@58: } nuclear@58: return TRUE; nuclear@58: } nuclear@58: nuclear@58: extern "C" { nuclear@58: nuclear@58: __declspec(dllexport) const TCHAR *LibDescription() nuclear@58: { nuclear@58: return L"Goat3D exporter stub"; nuclear@58: } nuclear@58: nuclear@58: __declspec(dllexport) int LibNumberClasses() nuclear@58: { nuclear@58: return 1; nuclear@58: } nuclear@58: nuclear@58: __declspec(dllexport) ClassDesc *LibClassDesc(int i) nuclear@58: { nuclear@58: return i == 0 ? &class_desc : 0; nuclear@58: } nuclear@58: nuclear@58: __declspec(dllexport) ULONG LibVersion() nuclear@58: { nuclear@58: return Get3DSMAXVersion(); nuclear@58: } nuclear@58: nuclear@58: __declspec(dllexport) int LibInitialize() nuclear@58: { nuclear@58: static char path[1024]; nuclear@58: nuclear@58: SHGetFolderPathA(0, CSIDL_PERSONAL, 0, 0, path); nuclear@58: strcat(path, "/testexpstub.log"); nuclear@58: nuclear@58: if((logfile = fopen(path, "w"))) { nuclear@58: setvbuf(logfile, 0, _IONBF, 0); nuclear@58: } nuclear@58: return TRUE; nuclear@58: } nuclear@58: nuclear@58: __declspec(dllexport) int LibShutdown() nuclear@58: { nuclear@58: if(logfile) { nuclear@58: fclose(logfile); nuclear@58: logfile = 0; nuclear@58: } nuclear@58: return TRUE; nuclear@58: } nuclear@58: nuclear@58: } // extern "C"