【问题标题】:Maya API: How to resolve these unresolved external symbol issues?Maya API:如何解决这些未解决的外部符号问题?
【发布时间】:2020-08-01 00:34:10
【问题描述】:

我正在尝试学习 Maya C++ API,并且能够使用本教程编译一些简单的“Hello World”类型插件:https://nccastaff.bournemouth.ac.uk/jmacey/MayaAPI/Windows/index.md.html

然后我尝试编译这个插件,该插件显然来自 2003 年出版的“完整的 Maya 编程”一书:

https://github.com/animformed/complete-maya-programming-book-files/tree/master/Volume-1/Plugins/BasicLocator

我获取了 .cpp 和 .h 文件并尝试构建新创建的 Visual Studio 2019 项目,但出现以下错误:

Severity    Code    Description Project File    Line    Suppression State
Warning C26495  Variable 'MArrayDataHandle::data' is uninitialized. Always initialize a member variable (type.6).   BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MArrayDataHandle.h    113 
Warning C26495  Variable 'MArrayDataHandle::fIsNull' is uninitialized. Always initialize a member variable (type.6).    BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MArrayDataHandle.h    113 
Warning C26812  The enum type 'MDAGDrawOverrideInfo::DrawOverrideDisplayType' is unscoped. Prefer 'enum class' over 'enum' (Enum.3).    BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MDagPath.h    79  
Warning C26812  The enum type 'MDAGDrawOverrideInfo::DrawOverrideLOD' is unscoped. Prefer 'enum class' over 'enum' (Enum.3).    BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MDagPath.h    81  
Warning C26495  Variable 'MDataHandle::f_data' is uninitialized. Always initialize a member variable (type.6).  BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MDataHandle.h 274 
Warning C26495  Variable 'MFnAttribute::ca' is uninitialized. Always initialize a member variable (type.6). BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MFnAttribute.h    72  
Warning C26812  The enum type 'MStatus::MStatusCode' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). BasicLocator    C:\Program Files\Autodesk\Maya2016.5\include\maya\MStatus.h 103 
Error   LNK2019 unresolved external symbol __imp_glBegin referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)    BasicLocator    C:\Users\Desktop02\Documents\Visual Studio 2019\maya_dev\complete_maya_programming_volume1\BasicLocator\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glEnd referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)  BasicLocator    C:\Users\Desktop02\Documents\Visual Studio 2019\maya_dev\complete_maya_programming_volume1\BasicLocator\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glPopAttrib referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)    BasicLocator    C:\Users\Desktop02\Documents\Visual Studio 2019\maya_dev\complete_maya_programming_volume1\BasicLocator\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glPushAttrib referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)   BasicLocator    C:\Users\Desktop02\Documents\Visual Studio 2019\maya_dev\complete_maya_programming_volume1\BasicLocator\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glVertex3f referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z) BasicLocator    C:\Users\Desktop02\Documents\Visual Studio 2019\maya_dev\complete_maya_programming_volume1\BasicLocator\BasicLocator.obj    1   
Error   LNK1120 5 unresolved externals  BasicLocator    C:\Users\Desktop02\Documents\Visual Studio 2019\maya_dev\complete_maya_programming_volume1\BasicLocator\BasicLocator.mll    1   

然后我听说从技术上讲,对于 Maya API 构建来说,使用 VS 2017 更安全,而且显然通过 CMake 之类的方法创建解决方案文件更安全,我尝试通过这些 cmake 文件创建一个新项目:

FindMaya.cmake:

if(NOT DEFINED MAYA_VERSION)
    set(MAYA_VERSION 2015 CACHE STRING "Maya version")
endif()

set(MAYA_COMPILED_DEFINITIONS "REQUIRE_IOSTREAM;_BOOL")

set(MAYA_INSTALL_BASE_SUFFIX "")
set(MAYA_LIB_SUFFIX "lib")
set(MAYA_INC_SUFFIX "include")
if(WIN32)
    # Windows
    set(MAYA_INSTALL_BASE_DEFAULT "C:/Program Files/Autodesk")
    set(OPENMAYA OpenMaya.lib)
    set(MAYA_COMPILED_DEFINITIONS "${MAYA_COMPILED_DEFINITIONS};NT_PLUGIN")
    set(MAYA_PLUGIN_EXTENSION ".mll")
elseif(APPLE)
    # Mac
    set(MAYA_INSTALL_BASE_DEFAULT "/Applications/Autodesk")
    set(OPENMAYA libOpenMaya.dylib)
    set(MAYA_LIB_SUFFIX "Maya.app/Contents/MacOS")
    set(MAYA_INC_SUFFIX "devkit/include")
    set(MAYA_COMPILED_DEFINITIONS "${MAYA_COMPILED_DEFINITIONS};OSMac_")
    set(MAYA_PLUGIN_EXTENSION ".bundle")
else(WIN32)
    # Linux
    # this is OLD CMake syntax where the last else statement must match the first if statement
    set(MAYA_INSTALL_BASE_DEFAULT "/usr/autodesk")
    set(MAYA_INSTALL_BASE_SUFFIX -x64)
    set(OPENMAYA libOpenMaya.so)
    set(MAYA_PLUGIN_EXTENSION ".so")
    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fPIC")
endif()

set(MAYA_INSTALL_BASE_PATH ${MAYA_INSTALL_BASE_DEFAULT} CACHE STRING "Root Maya installation path")
set(MAYA_LOCATION ${MAYA_INSTALL_BASE_PATH}/MAYA${MAYA_VERSION}${MAYA_INSTALL_BASE_SUFFIX})

find_path(MAYA_LIBRARY_DIR ${OPENMAYA}
    PATHS
        ${MAYA_LOCATION}
        $ENV{MAYA_LOCATION}
    PATH_SUFFIXES
        "${MAYA_LIB_SUFFIX}/"
    DOC "Maya Library Path"
)

find_path(MAYA_INCLUDE_DIR maya/MFn.h
    PATHS
        ${MAYA_LOCATION}
        $ENV{MAYA_LOCATION}
    PATH_SUFFIXES
        "${MAYA_INC_SUFFIX}/"
    DOC "Maya Include Path"
)

set(_MAYA_LIBRARIES OpenMaya OpenMayaAnim OpenMayaFX OpenMayaRender OpenMayaUI Foundation)
foreach(MAYA_LIB ${_MAYA_LIBRARIES})
    find_library(MAYA_${MAYA_LIB}_LIBRARY NAMES ${MAYA_LIB} PATHS ${MAYA_LIBRARY_DIR} NO_DEFAULT_PATH)
    set(MAYA_LIBRARIES ${MAYA_LIBRARIES} ${MAYA_${MAYA_LIB}_LIBRARY})
endforeach()

include(FindPackageHandleStandardArgs)
find_package_handle_standard_args(Maya DEFAULT_MSG MAYA_INCLUDE_DIR MAYA_LIBRARIES)

function(MAYA_PLUGIN _target)
    if(WIN32)
        set_target_properties(${_target} PROPERTIES
            LINK_FLAGS "/export:initializePlugin /export:uninitializePlugin")
    endif()
    set_target_properties(${_target} PROPERTIES
        COMPILE_DEFINITIONS "${MAYA_COMPILED_DEFINITIONS}"
        PREFIX ""
        SUFFIX ${MAYA_PLUGIN_EXTENSION}
    )
endfunction()

BasicLocator/CMakeLists.txt:

cmake_minimum_required(VERSION 2.6)
project(basicLocatorCmake)

set(CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR}/modules)

add_subdirectory(src)

BasicLocator/src/CMakeLists.txt:

set(SOURCE_FILES
    "PluginMain.cpp"
    "BasicLocator.cpp"
    "BasicLocator.h"
)

find_package(Maya REQUIRED)

include_directories(${MAYA_INCLUDE_DIR})
link_directories(${MAYA_LIBRARY_DIR})

add_library(${PROJECT_NAME} SHARED ${SOURCE_FILES})
target_link_libraries(${PROJECT_NAME} ${MAYA_LIBRARIES})

MAYA_PLUGIN(${PROJECT_NAME})

这似乎可以很好地创建一个 Visual Studio 项目解决方案,但是当我编译时出现类似的错误(减去警告):

Severity    Code    Description Project File    Line    Suppression State
Error   LNK1120 5 unresolved externals  basicLocatorCmake   C:\Users\Desktop02\Documents\Visual Studio 2017\maya_dev\complete_maya_programming_volume1\BasicLocator_cmake\build\src\Debug\basicLocatorCmake.mll 1   
Error   LNK2019 unresolved external symbol __imp_glBegin referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)    basicLocatorCmake   C:\Users\Desktop02\Documents\Visual Studio 2017\maya_dev\complete_maya_programming_volume1\BasicLocator_cmake\build\src\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glEnd referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)  basicLocatorCmake   C:\Users\Desktop02\Documents\Visual Studio 2017\maya_dev\complete_maya_programming_volume1\BasicLocator_cmake\build\src\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glPopAttrib referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)    basicLocatorCmake   C:\Users\Desktop02\Documents\Visual Studio 2017\maya_dev\complete_maya_programming_volume1\BasicLocator_cmake\build\src\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glPushAttrib referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z)   basicLocatorCmake   C:\Users\Desktop02\Documents\Visual Studio 2017\maya_dev\complete_maya_programming_volume1\BasicLocator_cmake\build\src\BasicLocator.obj    1   
Error   LNK2019 unresolved external symbol __imp_glVertex3f referenced in function "public: virtual void __cdecl BasicLocator::draw(class M3dView &,class MDagPath const &,enum M3dView::DisplayStyle,enum M3dView::DisplayStatus)" (?draw@BasicLocator@@UEAAXAEAVM3dView@@AEBVMDagPath@@W4DisplayStyle@2@W4DisplayStatus@2@@Z) basicLocatorCmake   C:\Users\Desktop02\Documents\Visual Studio 2017\maya_dev\complete_maya_programming_volume1\BasicLocator_cmake\build\src\BasicLocator.obj    1   

我感觉这与这些 .cpp 文件自 2003 年编写以来在某些地方已经过时有关,但我无法解读这些“过时”部分的确切位置,因为尝试搜索 M3dView 并不t 似乎真的想出了很多。

任何人都可以为我指出如何解决这些冲突的正确方向吗...?

Edit#1:忘了提,但我使用的是 Maya 2016.5

【问题讨论】:

  • 在 CMakeLists.txt 中,这些是什么? OpenMaya OpenMayaAnim OpenMayaFX OpenMayaRender 等?它们是 DLL 文件还是 .lib 文件?
  • 请以文本而不是图像的形式将错误消息添加到问题帖子中。另见How to Ask
  • 如评论,请将错误消息作为文本发布,因为不鼓励为此目的使用图像。另外,您确定您的机器上安装了 Maya:C:/Program Files/Autodesk
  • @squareskittles,感谢您的推荐,已将错误替换为文本而不是图像。是的,我确定,我的机器上安装了 Maya 2016.5
  • 所有 CMake MAYA_* 缓存变量是否与您机器上的实际路径一样正确且准确?其中一个可能是默认值,可能需要修改以匹配您的 Maya 版本和配置。

标签: c++ visual-studio cmake maya maya-api


【解决方案1】:

通过进一步的研究,我发现在最新版本的 Maya 中,要正确地在 Legacy 视口上绘制,您需要从 MHardwareRenderer(?) 指定指向渲染对象的指针。这是此插件的头文件和 cpp 文件的代码,现在可以使用

基本定位器.h:

//
// Copyright (C) 2001 David Gould 
//
#ifndef BASICLOCATOR_H
#define BASICLOCATOR_H

#include <maya/MPxLocatorNode.h> 
#include <maya/MString.h> 
#include <maya/MTypeId.h> 
#include <maya/MVector.h>
#include <maya/MDataBlock.h>
#include <maya/MDataHandle.h>
#include <maya/M3dView.h>
#include <maya/MDistance.h>
#include <maya/MFnUnitAttribute.h>
#include <maya/MFnNumericAttribute.h>
#include <maya/MFnMessageAttribute.h>
#include <maya/MFnTypedAttribute.h>
#include <maya/MPxManipContainer.h>
#include <maya/MPointArray.h>
#include <maya/MPlug.h>
#include <maya/MGlobal.h>
#include <math.h>

// legacy viewport includes
#include <maya/MHardwareRenderer.h>
#include <maya/MGLFunctionTable.h>

class BasicLocator : public MPxLocatorNode
{
public:
    virtual void draw( M3dView & view, const MDagPath & path, M3dView::DisplayStyle style, M3dView::DisplayStatus status );
    
    virtual bool isBounded() const;
    virtual MBoundingBox boundingBox() const; 

    static void *creator();
    static MStatus initialize();

    static const MTypeId typeId;
    static const MString typeName;

    // Attributes
    static MObject xWidth;
    static MObject zWidth;
    static MObject dispType;

private:
    bool getCirclePoints( MPointArray &pts ) const;
};


#endif

basicLocator.cpp

//
// Copyright (C) 2001 David Gould 
// 

#include "BasicLocator.h"
#include <maya/MGlobal.h>
#include <maya/MPointArray.h>
#include <maya/MFnDagNode.h>

const MTypeId BasicLocator::typeId( 0x00336 );
const MString BasicLocator::typeName( "basicLocator" );

MObject BasicLocator::xWidth;
MObject BasicLocator::zWidth;
MObject BasicLocator::dispType;

const double M_2PI = M_PI * 2.0;

bool BasicLocator::getCirclePoints( MPointArray &pts ) const
{
MStatus stat;
MObject thisNode = thisMObject();
MFnDagNode dagFn( thisNode  );  

MPlug xWidthPlug = dagFn.findPlug( xWidth, &stat );
float xWidthValue;
xWidthPlug.getValue( xWidthValue );

MPlug zWidthPlug = dagFn.findPlug( zWidth, &stat );
float zWidthValue;
zWidthPlug.getValue( zWidthValue );

MPlug typePlug = dagFn.findPlug( dispType, &stat );
short typeValue;
typePlug.getValue( typeValue );

unsigned int nCirclePts;

switch( typeValue )
   {
   case 0:
       nCirclePts = 4;
       break;
   case 1:
       nCirclePts = 5;
       break;
   default:
       nCirclePts = 20;
       break;
   }

pts.clear();
pts.setSizeIncrement( nCirclePts );
   
MPoint pt;
pt.y = 0.0;
   
const double angleIncr = M_2PI / (nCirclePts - 1);
double angle = 0.0;
unsigned int i=0;
for( ; i < nCirclePts; i++, angle+=angleIncr )
    {
    pt.x = xWidthValue * cos( angle );
    pt.z = zWidthValue * sin( angle );
    pts.append( pt );
    }

return true;
}

void BasicLocator::draw( M3dView & view, const MDagPath & path,
M3dView::DisplayStyle style, M3dView::DisplayStatus status )
{ 

// we need to add this to make sure Maya grabs the OpenGL commands
// we also need to make sure that all OpenGL commands are being used from gGLFT
static MGLFunctionTable *gGLFT = 0;
if (0 == gGLFT)
    gGLFT = MHardwareRenderer::theRenderer()->glFunctionTable();
//

view.beginGL(); 
gGLFT->glPushAttrib( GL_CURRENT_BIT );

MPointArray pts;
getCirclePoints( pts );

gGLFT->glBegin(GL_LINE_STRIP);
for( unsigned int i=0; i < pts.length(); i++ )
    gGLFT->glVertex3f( float(pts[i].x), float(pts[i].y), float(pts[i].z) );
gGLFT->glEnd();

gGLFT->glBegin(GL_LINES);
    gGLFT->glVertex3f( -0.5f, 0.0f, 0.0f );
    gGLFT->glVertex3f( 0.5f, 0.0f, 0.0f );

    gGLFT->glVertex3f( 0.0f, 0.0f, -0.5f );
    gGLFT->glVertex3f( 0.0f, 0.0f, 0.5f );
    gGLFT->glEnd();

gGLFT->glPopAttrib();
view.endGL();       
}

bool BasicLocator::isBounded() const
{ 
return true;
}

MBoundingBox BasicLocator::boundingBox() const
//
// N.B. It is important to have this bounding box function otherwise zoom selected and 
// zoom all won't work correctly.
//
{   
MPointArray pts;
getCirclePoints( pts );

MBoundingBox bbox;
for( unsigned int i=0; i < pts.length(); i++ )
    bbox.expand( pts[i] );
return bbox;
}


void *BasicLocator::creator()
{
return new BasicLocator();
}

MStatus BasicLocator::initialize()
{ 
MFnUnitAttribute unitFn;    
MFnNumericAttribute numFn;
MStatus stat;
    
xWidth = unitFn.create( "xWidth", "xw", MFnUnitAttribute::kDistance );
unitFn.setDefault( MDistance(1.0, MDistance::uiUnit()) );
unitFn.setMin( MDistance(0.0, MDistance::uiUnit()) );
unitFn.setKeyable( true );
stat = addAttribute( xWidth );
if (!stat) 
    {
    stat.perror( "Unable to add \"xWidth\" attribute" );
    return stat;
    } 

zWidth = unitFn.create( "zWidth", "zw", MFnUnitAttribute::kDistance );
unitFn.setDefault( MDistance(1.0, MDistance::uiUnit()) );
unitFn.setMin( MDistance(0.0, MDistance::uiUnit()) );
unitFn.setKeyable( true );
stat = addAttribute( zWidth );
if (!stat) 
    {
    stat.perror( "Unable to add \"zWidth\" attribute" );
    return stat;
    } 

dispType = numFn.create( "dispType", "att", MFnNumericData::kShort );
numFn.setDefault( 0);
numFn.setMin( 0 );
numFn.setMax( 2 );
numFn.setKeyable( true );
stat = addAttribute( dispType );
if (!stat) 
    {
    stat.perror( "Unable to add \"dispType\" attribute" );
    return stat;
    }

return MS::kSuccess;
}

现在就像 haggi krey 所说的,因为 Maya 使用 Viewport 2.0,这些绘图方法不再相关,所以一旦我找到这个插件的 Viewport 2.0 等效项,就会更新这张票...

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-12-19
    • 1970-01-01
    • 2017-07-20
    • 1970-01-01
    • 2011-09-03
    • 2010-11-20
    • 2017-11-15
    • 2011-02-13
    相关资源
    最近更新 更多