Linker error with basic C++ tutorial + AssImp


#1

I have attempted to modify the basic tutorial program to include an AssimpLoader. I can compile the program just fine, but when I attempt to link it (using the basic compiling and linking lines designated in the C++ tutorial, I get the following output:

main.o: In function `main':
main.cpp:(.text.startup+0x177): undefined reference to `AssimpLoader::AssimpLoader()'
main.cpp:(.text.startup+0x19b): undefined reference to `AssimpLoader::~AssimpLoader()'
main.cpp:(.text.startup+0x1d8): undefined reference to `AssimpLoader::~AssimpLoader()'
collect2: error: ld returned 1 exit status

My program looks as follows:


#include "pandaFramework.h"
#include "pandaSystem.h"
#include "assimpLoader.h"

int main(int argc, char *argv[]) {
    //open a new window framework
    PandaFramework framework;
    framework.open_framework(argc, argv);
      //set the window title to My Panda3D Window
    framework.set_window_title("My Panda3D Window");
      //open the window
    WindowFramework *window = framework.open_window();

    AssimpLoader modelLoader;
 
    //do the main loop, equal to run() in python
    framework.main_loop();
    //close the window framework
    framework.close_framework();
    return (0);
}

and my build shell script looks like:


#!/bin/bash

PYTHON_INCLUDE_DIR="/usr/include/python3.5"
PANDA3D_INCLUDE_DIR="${HOME}/Documents/panda3d/built/include"
PANDA3D_ASSIMP_INCLUDE_DIR="${HOME}/Documents/panda3d/pandatool/src/assimp"
ASSIMP_INCLUDE_DIR="${HOME}/Documents/assimp/include/assimp"
ASSIMP_INCLUDE_DIR2="${HOME}/Documents/assimp/include"
ASSIMP_LIB_DIR="${HOME}/Documents/assimp/lib"
PANDA3D_LIB_DIR="${HOME}/Documents/panda3d/built/lib"
EIGEN_INC_DIR="/usr/include/eigen3"



function compile_link {

    rm -rf main.o

    g++ -c main.cpp -o main.o -std=gnu++11 -O2 -I${PYTHON_INCLUDE_DIR} -I${EIGEN_INC_DIR} -I${PANDA3D_INCLUDE_DIR} -I${PANDA3D_ASSIMP_INCLUDE_DIR} -I${ASSIMP_INCLUDE_DIR} -I${ASSIMP_INCLUDE_DIR2}

    g++ main.o -o PandaTutorial -L${PANDA3D_LIB_DIR} -lp3framework -lpanda -lpandafx -lpandaexpress -lp3dtoolconfig -lp3dtool -lp3pystub -lp3direct -lp3assimp

}

compile_link

I’ve verified that if I comment out the line “AssimpLoader modelLoader;” the linker problgm goes away, and I am able to run the sample and get the expected window.

I know this sort of thing is a noobish question, but I’d be super-grateful for any help (and education!).

Thanks,

jonbitzen


#2

Well, you have not linked with -lp3assimp. However, that will still not work, because the AssimpLoader class is not exported from the dynamic library.

It is meant to be used as a loader plug-in. You can put load-file-type p3assimp in Config.prc to add the loader plug-in, or even load-file-type obj p3assimp to only load a particular extension with Assimp, and then you can use the regular model loading functions to load via Assimp.

Is there a particular reason you want to interface with AssimpLoader directly? If so, we will need to expose the class.


#3

Thanks for your response!

My goal is to write a cross-platform program like Open3Mod (which is a graphical front-end to AssImp), minus the Windows-only dependencies (it uses Windows forms, which for practical purposes aren’t supported on anything but Windows - mono has a partial implementation which is pretty broken).

I am attempting to use GTK3 as my GUI widget platform, and Panda3D as my renderer. I am trying to test the API in C++ first to make sure I know how it works before trying to write a Python binding (I plan to use the GTK3 Python bindings). Clearly a good choice in this case, since if I’d started with writing a python binding for the C++ class, I wouldn’t know which part(s) I’d done incorrectly.

I could take one of two approaches:

  • I could use the loader binding via the existing model loading API using the config.prc file, and later extend the existing API to include something to write model files (not sure that there are many general use-cases for this though)

  • I could look into the build files and figure out how to export the symbols in the shared library, and use them directly with my own Python binding.

I’m aware that in any case I’ll need to write a class to write via Assimp as well.

Thanks,

jonbitzen


#4

If you wish to export the class from libp3assimp.so you can simply modify the assimpLoader.h header and change the class definition like so:

class EXPCL_ASSIMP AssimpLoader : public TypedReferenceCount {

Then, recompile Panda. I’m happy to accept such a change to the main Panda3D repository; there is no good reason not to export this class if it is found useful, I suppose.

However, I would suggest that you just use the high-level Panda loader API unless you have a compelling reason not to. The high-level Loader interface does support loader plug-ins that can also save files, although this is not (yet) implemented for Assimp.

Best of luck with your project!