Revit API로 공유 매개변수 일괄 생성하고 카테고리에 바인딩하기

BIM 개발 워크스테이션에서 3D 모델과 코드 에디터를 함께 띄운 모습

Revit에서 물량·일람표·필터를 제대로 다루려면 결국 공유 매개변수(Shared Parameter)를 손에 익혀야 한다. 프로젝트 하나에 쓰이는 사용자 매개변수가 수십 개를 넘어가면, 이걸 손으로 하나씩 만들고 카테고리마다 바인딩하는 작업은 지루할 뿐 아니라 실수가 쌓이는 지점이 된다. 이름을 한 글자 다르게 치거나, 벽에는 넣고 기둥에는 빠뜨리거나, 인스턴스로 넣어야 할 것을 타입으로 넣는 식이다. Revit API로 이 과정을 코드로 옮기면 회사 표준 매개변수 세트를 프로젝트마다 동일하게, 단추 한 번으로 심을 수 있다. 이 글은 공유 매개변수의 구조부터 실제 C# 바인딩 코드까지 순서대로 정리한다.

■ 공유 매개변수가 패밀리·프로젝트 매개변수와 다른 점

Revit의 사용자 매개변수는 크게 세 종류다. 셋의 차이를 모르면 “일람표에 값이 안 나온다”는 문제로 반나절을 허비하게 된다.

종류 저장 위치 일람표 노출 여러 패밀리·프로젝트 공유
패밀리 매개변수 해당 패밀리 안 불가(직접 노출 안 됨) 불가
프로젝트 매개변수 프로젝트 파일 안 가능 불가(그 프로젝트 한정)
공유 매개변수 외부 .txt 파일 + GUID 가능 가능

핵심은 공유 매개변수만이 GUID라는 전역 식별자를 갖는다는 것이다. 일람표에 넣고 싶거나, 태그로 뽑고 싶거나, IFC로 내보낼 때 매핑되기를 바란다면 공유 매개변수여야 한다. 패밀리 안에서 만든 패밀리 매개변수는 프로젝트 일람표에 나오지 않는데, 이 지점이 처음 쓰는 사람이 가장 자주 걸리는 함정이다.

■ 공유 매개변수 파일(.txt)의 구조

공유 매개변수의 실체는 텍스트 파일이다. Revit은 이 파일을 열어 정의(Definition)를 읽고, 그중 필요한 것을 프로젝트에 바인딩한다. 파일은 탭으로 구분된 세 종류의 줄로 이뤄진다.

줄 종류 의미 주요 필드
META 파일 버전 정보 VERSION, MINVERSION
GROUP 매개변수 그룹(DefinitionGroup) ID, NAME
PARAM 개별 매개변수(ExternalDefinition) GUID, NAME, DATATYPE, GROUP, VISIBLE

여기서 그룹은 API의 DefinitionGroups에, 각 PARAM 줄은 ExternalDefinition에 대응한다. 파일을 직접 편집할 일은 드물고, 보통 Revit UI나 API로 만든다. 다만 구조를 알아 두면 “왜 이 매개변수가 그 그룹에 있지?” 같은 의문이 풀린다. 회사 표준 파일은 반드시 한 곳에 두고 버전 관리해야 한다. 각자 로컬에서 만든 파일로 작업하면 이름은 같지만 GUID가 다른 매개변수가 두 벌 생기고, 프로젝트를 합칠 때 일람표가 조용히 어긋난다.

3D BIM 모델의 파라메트릭 요소와 데이터 일람표 시각화

■ 바인딩의 두 갈래: InstanceBinding과 TypeBinding

정의를 프로젝트에 붙이는 것을 바인딩(Binding)이라 한다. 여기서 선택은 둘 중 하나다.

  • InstanceBinding — 배치된 요소 하나하나가 각자 값을 갖는다. 실번호, 검토 상태, 시공 순서처럼 개체마다 다른 값에 쓴다.
  • TypeBinding — 같은 타입을 쓰는 모든 요소가 값을 공유한다. 방화 등급, 벽 구성, 제조사처럼 타입에 종속된 값에 쓴다.

둘 다 CategorySet에 담긴 카테고리(벽·기둥·문 등)에 대해 적용된다. 한 번 정한 인스턴스/타입 성격은 나중에 바꾸기 번거로우니 처음에 신중히 고른다.

■ C# 코드: 공유 매개변수 일괄 생성 후 카테고리에 바인딩

아래는 공유 매개변수 파일을 열어 그룹과 정의를 준비하고, 벽·기둥에 인스턴스 매개변수로 바인딩하는 전체 흐름이다. 문서를 수정하므로 반드시 Transaction 안에서 실행한다.

[Transaction(TransactionMode.Manual)]
public class BindSharedParam : IExternalCommand
{
    public Result Execute(ExternalCommandData cData, ref string msg, ElementSet e)
    {
        UIApplication uiapp = cData.Application;
        Application app = uiapp.Application;
        Document doc = uiapp.ActiveUIDocument.Document;

        // 1) 공유 매개변수 파일 확보 (경로 미지정 시 null 방어)
        if (string.IsNullOrEmpty(app.SharedParametersFilename))
        {
            app.SharedParametersFilename = @"C:\BIM\SharedParams_Std.txt";
        }
        DefinitionFile defFile = app.OpenSharedParameterFile();
        if (defFile == null)
        {
            msg = "공유 매개변수 파일을 열 수 없습니다.";
            return Result.Failed;
        }

        // 2) 그룹 찾기 or 생성
        DefinitionGroup group = defFile.Groups.get_Item("ProjectData")
                                ?? defFile.Groups.Create("ProjectData");

        // 3) 정의(ExternalDefinition) 확보 - 이미 있으면 재사용
        ExternalDefinition def = group.Definitions.get_Item("검토상태") as ExternalDefinition;
        if (def == null)
        {
            var opt = new ExternalDefinitionCreationOptions(
                          "검토상태", SpecTypeId.String.Text);
            opt.UserModifiable = true;
            opt.Description = "요소별 도면 검토 상태";
            def = group.Definitions.Create(opt) as ExternalDefinition;
        }

        // 4) 바인딩할 카테고리 모으기
        var catSet = app.Create.NewCategorySet();
        catSet.Insert(Category.GetCategory(doc, BuiltInCategory.OST_Walls));
        catSet.Insert(Category.GetCategory(doc, BuiltInCategory.OST_Columns));

        // 5) 인스턴스 바인딩 생성 후 트랜잭션 안에서 삽입
        InstanceBinding binding = app.Create.NewInstanceBinding(catSet);
        using (Transaction t = new Transaction(doc, "공유 매개변수 바인딩"))
        {
            t.Start();
            BindingMap map = doc.ParameterBindings;
            if (!map.Insert(def, binding, GroupTypeId.Data))
            {
                // 이미 있으면 ReInsert로 카테고리 갱신
                map.ReInsert(def, binding, GroupTypeId.Data);
            }
            t.Commit();
        }
        return Result.Succeeded;
    }
}

여러 매개변수를 한꺼번에 심으려면 3~5단계를 이름·데이터형·카테고리 목록을 담은 배열로 돌리면 된다. 표로 정의를 관리하고 반복문으로 Insert하는 구조가 실무에서 가장 유지보수하기 편하다.

■ Insert가 실패하는 흔한 원인

증상 원인 대응
OpenSharedParameterFile가 null SharedParametersFilename 미지정 또는 경로 없음 경로 먼저 설정·존재 확인
Insert가 false 반환 같은 정의가 이미 바인딩됨 ReInsert로 카테고리 갱신
모델리스 예외 Transaction 밖에서 수정 시도 Start~Commit 안으로 이동
일람표에 값 없음 인스턴스/타입 바인딩 선택 오류 값의 성격에 맞게 재바인딩

노트북으로 Revit 3D 모델을 다루는 엔지니어

■ 눈여겨볼 것

공유 매개변수의 실제 식별자는 이름이 아니라 GUID다. 이름이 같아도 GUID가 다르면 Revit은 다른 매개변수로 취급하고, 그 순간 일람표와 필터가 조용히 어긋난다. 자동화 스크립트를 만들 때는 매개변수를 새로 만들기 전에 같은 이름이 이미 바인딩돼 있는지 BindingMap을 훑어 확인하는 절차를 반드시 넣는다. 또 하나, Revit 2022 이후로 매개변수 데이터형은 옛 ParameterType 열거형이 아니라 SpecTypeId·GroupTypeId 같은 ForgeTypeId 기반으로 바뀌었다. 오래된 예제 코드를 그대로 붙여 넣으면 컴파일되지 않으므로, 대상 Revit 버전의 API에 맞춰 타입 식별자를 확인해야 한다.

■ 이런 분께 도움이 됩니다

  • Revit API를 시작하는 개발자·BIM 엔지니어 — 바인딩은 API 입문에서 가장 자주 막히는 지점이다
  • 사무소 BIM 표준 담당자 — 매개변수 세트를 프로젝트마다 자동으로 심을 수 있다
  • 물량·일람표를 다루는 실무자 — 일람표가 어긋나는 원인의 상당수가 매개변수 중복이다

■ 참고

공유 매개변수 파일 경로는 사용자 PC마다 다르게 잡히기 쉬우므로, 사내 스크립트에서는 네트워크 공유 폴더나 형상관리 저장소의 고정 경로를 코드에 넣어 두는 편이 안전하다. 데이터형·GUID·바인딩 방식은 Revit 버전에 따라 세부가 달라질 수 있으니, 배포 전 실제 대상 버전에서 한 번 실행해 일람표에 값이 정상적으로 노출되는지 확인한다.


공식 참고 자료 및 적용 범위

이 글은 Revit API를 이용한 공유 매개변수 관리의 일반적 방법을 설명합니다. API 클래스·바인딩 동작·권한과 실행 결과는 Revit API 버전, 문서 상태, 카테고리와 프로젝트 표준에 따라 달라질 수 있습니다.

아래 자료는 확인일 기준의 제조사·표준기구 또는 공공기관 공식 문서입니다. 제품 기능·표준·정책은 개정될 수 있으므로 실제 프로젝트 적용 전에는 사용 중인 버전의 최신 원문과 프로젝트 기준을 확인하세요.

확인일: 2026-08-15