Skip to content
CTRL 섹션 중심 문서 시스템
Tooling

Maya C++ 플러그인 실습편 - Windows에서 Hello World까지

Maya 버전 고정, DevKit 준비, Visual Studio와 CMake 설정, 첫 C++ 명령 플러그인 빌드와 로드 과정을 Windows 기준으로 정리한 실습 가이드.

이 문서는 프로그래밍에 관심 있는 리거를 위한 Maya C++ 플러그인 입문 다음 단계에 해당하는 실습편이다.

개념편이 "무엇이 무엇인지 구분하는 문서"였다면, 이번 문서는 실제로 손을 움직여서 Windows에서 첫 .mll 파일을 만들고, Maya에 로드하고, 커맨드를 실행해보는 과정을 다룬다.

목표는 거창하지 않다.

  1. Maya 버전을 하나 고정한다.
  2. 그 버전에 맞는 DevKit과 빌드 환경을 준비한다.
  3. 가장 작은 C++ 명령 플러그인을 빌드한다.
  4. Maya에서 로드한다.
  5. Script Editor에서 커맨드를 호출해 본다.

이 한 번의 왕복이 성공하면, 그다음부터는 커스텀 노드와 뷰포트 확장도 "더 큰 버전의 같은 문제"로 보이기 시작한다.

이 문서에서 전제하는 것

아래는 이미 되어 있다고 가정한다.

  • Maya를 한 번 이상 실행해본 적이 있다
  • Script Editor를 열어본 적이 있다
  • Python이나 MEL을 아주 조금이라도 만져본 적이 있다
  • Visual Studio 설치가 낯설지 않다

아래는 아직 몰라도 된다.

  • MPxNode
  • MDataBlock
  • Viewport 2.0
  • Manipulator
  • DG evaluation의 세부 흐름

이번 문서의 목적은 어디까지나 첫 C++ 플러그인 빌드와 로드에 성공하는 것이다.

1. 가장 먼저 해야 할 일: Maya 버전을 고정한다

입문자가 가장 많이 하는 실수는 "일단 최신 문서를 본다"와 "내 컴퓨터에 깔린 Maya 버전"을 섞어 생각하는 것이다.

플러그인 개발에서는 버전이 매우 중요하다.

  • DevKit 버전
  • Maya 실행 버전
  • 빌드에 사용한 툴체인
  • 최종 .mll이 로드되는 대상 버전

이 네 가지가 서로 맞아야 한다.

특히 Autodesk 문서도 빌드된 플러그인은 더 낮은 Maya 버전에서 로드할 수 없다고 설명한다.
관련 시작점:

처음엔 이렇게 정하는 편이 좋다.

  • 내가 실제로 사용하는 Maya 버전 하나만 고정한다
  • 문서도 그 버전에 맞춰 본다
  • DevKit도 그 버전에 맞춰 받는다
  • 빌드 출력도 그 버전에서 먼저 테스트한다

버전이 흔들리면 입문자가 겪는 오류의 절반은 설명하기 어려워진다.

2. Windows에서 준비할 것

실습 전에 필요한 것은 아래 다섯 가지다.

  1. Maya 본체
  2. 해당 버전의 Maya DevKit
  3. Visual Studio
  4. CMake
  5. 빌드 결과를 둘 위치와 Maya가 읽을 플러그인 경로

Autodesk 공식 시작점:

주의할 점은 Visual Studio 버전 요구사항이 Maya 버전에 따라 달라질 수 있다는 것이다.
최근 DevKit 문서에서는 Maya 2024 계열부터 Visual Studio 2022를 요구하는 내용이 보인다.
그래서 "내 Maya 버전의 build environment 문서"를 먼저 읽고 그대로 맞추는 것이 안전하다.

3. 폴더와 경로를 먼저 정리한다

입문자가 편하게 시작하려면 경로를 너무 복잡하게 잡지 않는 편이 좋다.

예를 들어 아래처럼 분리하면 된다.

C:\maya-dev\
  devkit\
  projects\
    hello_cmd\
  plugins\

추천 역할은 다음과 같다.

  • devkit: Autodesk에서 받은 DevKit 압축을 푼 위치
  • projects: Visual Studio/CMake 프로젝트를 둘 위치
  • plugins: 빌드된 .mll을 모을 위치

그리고 Maya 쪽에서는 아래 중 하나로 연결한다.

  1. MAYA_PLUG_IN_PATHplugins 폴더를 가리키게 한다
  2. Plugin Manager에서 직접 .mll을 로드한다
  3. Script Editor에서 loadPlugin으로 수동 로드한다

처음에는 2번이나 3번이 더 명확하다.
자동 로딩은 나중에 붙여도 된다.

4. 첫 성공은 DevKit 예제로 하는 편이 좋다

바로 내 코드부터 빌드하려고 하면, 오류가 났을 때 원인이 너무 많아진다.

  • 내 코드가 틀린 건지
  • include path가 틀린 건지
  • 라이브러리 링크가 틀린 건지
  • CMake 설정이 틀린 건지
  • Maya 버전이 안 맞는 건지

그래서 첫 성공은 DevKit 예제로 하는 편이 안전하다.

Autodesk 문서의 추천 시작점:

이 단계의 목표는 단 하나다.

"Autodesk가 준 예제를 내 컴퓨터에서 빌드해서 Maya가 실제로 로드한다."

이게 성공하면 내 환경은 최소한 살아 있다.

5. CMake와 Visual Studio로 첫 빌드를 해본다

DevKit 예제를 기준으로 가장 먼저 할 일은 프로젝트 생성이다.

Autodesk의 Building with CMake 문서에 따르면, DevKit 예제는 CMake 기반으로 프로젝트를 생성한 뒤 IDE에서 빌드하거나 cmake --build로 빌드할 수 있다.

Windows에서는 보통 이런 흐름을 쓴다.

cmake -S . -B build -G "Visual Studio 17 2022"
cmake --build build --config Release

실제 generator 이름은 설치된 Visual Studio와 Maya 버전에 따라 달라질 수 있다.
중요한 것은 해당 Maya 버전 문서에 적힌 권장 툴체인에 맞추는 것이다.

처음에는 아래만 확인하면 충분하다.

  • CMake configure가 성공하는가
  • Visual Studio 솔루션이 생성되는가
  • Release 빌드가 통과하는가
  • .mll 파일이 실제로 생기는가

6. 첫 커스텀 명령 플러그인의 최소 구조를 이해한다

DevKit 예제로 첫 성공을 한 뒤에는, 이제 구조를 직접 읽는 단계로 넘어간다.

가장 작은 명령 플러그인은 보통 아래 요소를 가진다.

  • initializePlugin()
  • uninitializePlugin()
  • MFnPlugin
  • MPxCommand
  • doIt()

Autodesk 문서도 모든 플러그인은 initializePlugin()uninitializePlugin() 이 필요하다고 설명한다.
이 두 함수가 없으면 Maya는 플러그인을 로드하지 못한다.

7. 직접 읽어볼 수 있는 최소 예제

아래 코드는 구조를 이해하기 위한 최소한의 예제다.
Script Editor에 "helloCtrl" 이라는 새 명령을 등록하고, 실행하면 메시지를 출력한다.

#include <maya/MFnPlugin.h>
#include <maya/MGlobal.h>
#include <maya/MPxCommand.h>
#include <maya/MStatus.h>

class HelloCtrlCommand : public MPxCommand
{
public:
    static void* creator()
    {
        return new HelloCtrlCommand();
    }

    MStatus doIt(const MArgList&) override
    {
        MGlobal::displayInfo("Hello from CTRL Maya C++ plugin.");
        return MS::kSuccess;
    }
};

MStatus initializePlugin(MObject obj)
{
    MFnPlugin plugin(obj, "CTRL", "1.0.0", "Any");
    return plugin.registerCommand("helloCtrl", HelloCtrlCommand::creator);
}

MStatus uninitializePlugin(MObject obj)
{
    MFnPlugin plugin(obj);
    return plugin.deregisterCommand("helloCtrl");
}

이 예제에서 봐야 할 포인트는 문법보다 구조다.

  • HelloCtrlCommand 는 Maya가 실행할 커맨드 클래스다
  • creator() 는 Maya가 객체를 만들 때 쓰는 팩토리 역할이다
  • doIt() 는 커맨드 본체다
  • initializePlugin() 에서 Maya에 커맨드를 등록한다
  • uninitializePlugin() 에서 등록을 해제한다

즉, 플러그인은 단순한 C++ 프로그램이 아니라 Maya의 등록 시스템에 타입을 추가하는 라이브러리라고 생각하는 편이 정확하다.

8. 처음에는 왜 MPxCommand부터 시작하는가

입문자가 MPxNode보다 MPxCommand부터 보는 이유는 단순하다.

MPxCommand는 한 번 호출되는 흐름이 비교적 명확하기 때문이다.

  • 로드
  • 등록
  • 호출
  • 메시지 출력
  • 언로드

반면 MPxNode는 여기서 바로 개념이 늘어난다.

  • 속성 선언
  • MObject 기반 속성 핸들
  • compute()
  • dirty propagation
  • DG 평가 시점

그래서 첫 실습은 명령 플러그인으로 시작하는 편이 좋다.
커맨드 플러그인에서 Maya가 나를 호출하는 방식을 먼저 체감하면, 이후 노드 플러그인도 훨씬 덜 낯설다.

9. Maya에서 플러그인을 로드하는 법

빌드가 끝나서 .mll 파일이 생겼다면, 이제 Maya에서 실제로 읽히는지 확인해야 한다.

가장 흔한 방법은 두 가지다.

방법 1. Plugin Manager 사용

  1. Maya에서 Windows > Settings/Preferences > Plug-in Manager 를 연다
  2. 만든 .mll 파일을 찾는다
  3. Loaded 를 켠다
  4. 필요하면 Auto load 를 켠다

관련 문서:

방법 2. Script Editor에서 수동 로드

import maya.cmds as cmds
cmds.loadPlugin(r"C:\maya-dev\plugins\helloCtrl.mll")

경로를 직접 지정하는 방식은 가장 단순하고, 지금 어떤 파일을 읽는지 분명해서 디버깅할 때 좋다.

10. 로드가 성공했는지 확인하는 법

플러그인이 로드되었는지 확인할 때는 "에러가 안 났다"만 보면 부족하다.

아래까지 확인해야 한다.

  1. Plugin Manager에 실제로 로드 상태가 표시되는가
  2. Script Editor에 에러가 없는가
  3. 등록한 명령을 실제로 호출할 수 있는가

예를 들어 위 예제를 빌드했다면 Script Editor에서 이렇게 테스트한다.

import maya.cmds as cmds
cmds.helloCtrl()

혹은 MEL 스타일 호출이라면:

helloCtrl;

정상이라면 Script Editor나 Output Window에 "Hello from CTRL Maya C++ plugin." 같은 메시지가 출력된다.

여기까지 오면 첫 성공이다.

11. 초반에 가장 자주 막히는 문제

입문자는 거의 비슷한 문제에서 막힌다.

1. Maya 버전과 빌드 버전이 안 맞는다

증상:

  • 로드 자체가 실패한다
  • Plugin Manager에 경고가 뜬다
  • API version mismatch 같은 메시지가 나온다

대응:

  • 어느 Maya에서 빌드했고 어느 Maya에서 로드하는지 다시 확인한다
  • DevKit 버전도 함께 맞춘다

2. .mll은 있는데 종속 DLL 문제로 로드가 안 된다

증상:

  • 파일은 보이는데 로드 실패
  • Visual C++ runtime이나 추가 DLL 누락 문제

대응:

  • Visual Studio 런타임 설치 여부 확인
  • 외부 라이브러리를 링크했다면 해당 DLL 경로도 확인
  • 처음 실습은 외부 라이브러리 없는 예제로 시작

3. 언로드하지 않고 다시 빌드한다

Autodesk 문서도 플러그인이 동적 라이브러리를 사용한다면 재컴파일 전에 언로드해야 한다고 안내한다.
로드된 상태로 덮어쓰기 빌드를 반복하면 충돌이나 크래시 원인이 된다.

관련 문서:

그래서 입문 단계에서는 이 습관을 들이는 것이 좋다.

  1. Maya에서 언로드
  2. 다시 빌드
  3. 다시 로드

4. 환경 변수와 실제 경로를 혼동한다

특히 MAYA_LOCATION, DEVKIT_LOCATION, MAYA_PLUG_IN_PATH 는 이름이 비슷해서 헷갈리기 쉽다.

  • MAYA_LOCATION: Maya 설치 위치
  • DEVKIT_LOCATION: DevKit 위치
  • MAYA_PLUG_IN_PATH: Maya가 플러그인을 찾는 경로

이 셋은 역할이 다르다.

12. 첫 성공 뒤에 바로 해볼 만한 다음 단계

첫 커맨드 플러그인이 성공했다면, 그다음은 아래 순서가 좋다.

단계 1. doIt() 안에서 인자를 받아본다

  • MArgList
  • 문자열, 숫자 인자 파싱
  • 호출 형식 제어

단계 2. undo 가능한 커맨드로 바꿔본다

  • isUndoable()
  • redoIt()
  • undoIt()

이 단계에서 "Maya 커맨드는 일반 함수 호출과 다르다"는 감각이 생긴다.

단계 3. 씬 데이터를 읽는 명령으로 바꿔본다

  • 현재 선택 가져오기
  • 선택 노드 이름 출력
  • DAG 경로 탐색

이 단계에서 Python API로 해봤던 실험과 C++ API가 연결되기 시작한다.

단계 4. 그다음에 MPxNode로 넘어간다

커맨드가 "실행" 중심이라면, 노드는 "장면 구조" 중심이다.
리거에게 중요한 학습은 결국 여기서 시작된다.

13. 리거 기준으로 이 실습이 왜 중요한가

리거는 종종 이렇게 생각한다.

"결국 나한테 필요한 건 솔버나 커스텀 노드인데, 왜 Hello World 같은 걸 먼저 하지?"

이 질문은 타당하다.
하지만 Hello World를 먼저 하는 이유는 기능이 중요해서가 아니라, Maya 플러그인 개발의 왕복 구조 전체를 가장 작은 단위로 체험할 수 있기 때문이다.

그 왕복 구조는 항상 같다.

  1. Maya 버전 고정
  2. DevKit 준비
  3. 빌드
  4. .mll 생성
  5. Maya 로드
  6. 명령 또는 노드 등록
  7. Maya 내부에서 호출
  8. 수정 후 다시 언로드/빌드/로드

커스텀 솔버도, 노드도, 뷰포트 UI도 결국 이 루프를 더 복잡하게 확장한 것이다.

14. 이번 문서의 체크리스트

이 문서를 다 읽고 나서 아래가 되면 성공이다.

  • 내 Maya 버전을 하나 고정했다
  • DevKit을 같은 버전으로 준비했다
  • Visual Studio와 CMake로 예제를 빌드해봤다
  • .mll 파일을 Maya에서 로드해봤다
  • Script Editor에서 새 명령을 호출해봤다

이 다섯 가지가 되면, 그다음 문서는 자연스럽게 MPxNode, 속성, compute(), dirty propagation으로 넘어갈 수 있다.

다음 문서에서 다룰 것

실습편 다음 단계는 보통 아래 두 갈래다.

  1. MPxCommand 심화
  2. MPxNode 입문

리거라면 보통 2번이 더 중요하다.
왜냐하면 결국 관심은 "Maya에 새로운 계산 단위를 어떻게 넣는가"로 이동하기 때문이다.

다음 문서로는 Maya C++ 플러그인 실습편 - MPxNode 입문과 compute 감각 잡기가 자연스럽다.

그 다음 문서에서는 아래를 다룬다.

  • MPxNode 최소 구조
  • 속성 선언과 등록
  • 입력/출력 플러그
  • compute() 와 dirty
  • Maya가 노드를 언제 평가하는가

여기까지 오면 비로소 "스크립터에서 플러그인 개발자 쪽으로 넘어가는 문턱"이 보이기 시작한다.