Een ribbon-knop toevoegen aan AutoCAD is dé manier om je add-in professioneel te integreren. Gebruikers verwachten dat tools teruggevonden worden in het lint, niet via de commandoregel. In dit artikel bouw je stap voor stap een eigen ribbon-tab met panels en knoppen in C#, inclusief iconen en tooltips.
Architectuur van het AutoCAD-lint
Het lint (Ribbon) bestaat uit een hiërarchie: RibbonControl (het lint zelf) → RibbonTab → RibbonPanelSource + RibbonPanel → RibbonRowPanel → RibbonButton. Je voegt je eigen tab toe naast de standaard AutoCAD-tabs zoals Home, Insert, enz.
NuGet-referenties en namespaces
Voor ribbonwerk heb je extra assemblies nodig naast de standaard AutoCAD-referenties:
// Project-referenties (niet via NuGet, maar via GAC/installatiemap):
// AcWindows.dll → voor RibbonControl, RibbonTab, ...
// AdWindows.dll → voor WPF-integratie
// PresentationCore.dll → voor BitmapImage
using Autodesk.AutoCAD.Ribbon;
using Autodesk.Windows;
using System.Windows.Media.Imaging;
using System.Reflection;
Ribbon-tab aanmaken bij opstarten
Gebruik het ApplicationInitialized-event om de tab te laden nadat AutoCAD volledig is opgestart. Luister ook naar Workspace.WorkspaceLoaded zodat de tab heraaangemaakt wordt als de gebruiker van werkruimte wisselt.
public class MijnPlugin : IExtensionApplication
{
public void Initialize()
{
// Wacht tot AutoCAD volledig geladen is
Application.Idle += OnFirstIdle;
}
private bool _ribbonAangemaakt = false;
private void OnFirstIdle(object sender, EventArgs e)
{
if (_ribbonAangemaakt) return;
Application.Idle -= OnFirstIdle;
MaakRibbon();
_ribbonAangemaakt = true;
// Herstellen na workspace-switch
ComponentManager.ItemInitialized += (s, args) =>
{
if (args.NewObject is RibbonControl)
MaakRibbon();
};
}
public void Terminate() { }
}
Tab, panel en knoppen toevoegen
private void MaakRibbon()
{
var ribbon = ComponentManager.Ribbon;
if (ribbon == null) return;
// Verwijder bestaande tab om duplicaten te voorkomen
var bestaand = ribbon.Tabs.FirstOrDefault(t => t.Id == "KleverCAD_Tab");
if (bestaand != null) ribbon.Tabs.Remove(bestaand);
// Tab aanmaken
var tab = new RibbonTab
{
Id = "KleverCAD_Tab",
Title = "KleverCAD",
IsActive = true
};
// Panel aanmaken
var panelSource = new RibbonPanelSource { Title = "Automatisering" };
var panel = new RibbonPanel { Source = panelSource };
// Rijpaneel voor knoppen op één rij
var rij = new RibbonRowPanel();
// Knop 1: grote knop met icoon
var knopBlokken = MaakKnop(
id: "btn_blokken",
tekst: "Blokken",
tooltip: "Voeg standaardblokken in",
commando: "INVOEGBLOK",
iconPad: "Resources/blokken_32.png",
groot: true
);
// Knop 2: kleine knop
var knopPdf = MaakKnop(
id: "btn_pdf",
tekst: "PDF",
tooltip: "Exporteer naar PDF",
commando: "PDFEXPORT",
iconPad: "Resources/pdf_16.png",
groot: false
);
rij.Items.Add(knopBlokken);
rij.Items.Add(new RibbonSeparator());
rij.Items.Add(knopPdf);
panelSource.Items.Add(rij);
panel.Source = panelSource;
tab.Panels.Add(panel);
ribbon.Tabs.Add(tab);
}
Knop aanmaken met icoon
private RibbonButton MaakKnop(string id, string tekst, string tooltip,
string commando, string iconPad, bool groot)
{
var knop = new RibbonButton
{
Id = id,
Text = tekst,
ToolTip = new RibbonToolTip { Title = tekst, Content = tooltip },
CommandHandler = new RibbonCommandHandler(commando),
ShowText = true,
Size = groot ? RibbonItemSize.Large : RibbonItemSize.Standard,
Orientation = groot ? System.Windows.Controls.Orientation.Vertical
: System.Windows.Controls.Orientation.Horizontal
};
// Icoon laden vanuit embedded resource
var asm = Assembly.GetExecutingAssembly();
var stream = asm.GetManifestResourceStream(
$"{asm.GetName().Name}.{iconPad.Replace('/', '.')}");
if (stream != null)
{
var img = new BitmapImage();
img.BeginInit();
img.StreamSource = stream;
img.EndInit();
if (groot)
knop.LargeImage = img; // 32×32
else
knop.Image = img; // 16×16
}
return knop;
}
CommandHandler implementeren
public class RibbonCommandHandler : System.Windows.Input.ICommand
{
private readonly string _commando;
public RibbonCommandHandler(string commando) => _commando = commando;
public bool CanExecute(object parameter) => true;
public void Execute(object parameter)
{
var doc = Application.DocumentManager.MdiActiveDocument;
if (doc != null)
doc.SendStringToExecute(_commando + "\n", true, false, false);
}
public event EventHandler CanExecuteChanged { add { } remove { } }
}
Toggle-knop (aan/uit)
Een toggle-knop heeft een gecheckte en een niet-gecheckte staat, handig voor modi zoals "snapping aan" of "lagen zichtbaar".
var toggle = new RibbonToggleButton
{
Id = "btn_modus",
Text = "Modus",
IsChecked = false,
CommandHandler = new ToggleCommandHandler(),
};
Split-knop (dropdown met opties)
var splitKnop = new RibbonSplitButton { Text = "Exporteer", ShowText = true };
splitKnop.Items.Add(MaakKnop("btn_pdf", "PDF", "Exporteer PDF", "PDFEXPORT", "pdf_16.png", false));
splitKnop.Items.Add(MaakKnop("btn_dwg", "DWG", "Exporteer DWG", "SAVEAS", "dwg_16.png", false));
splitKnop.Items.Add(MaakKnop("btn_dxf", "DXF", "Exporteer DXF", "DXFOUT", "dxf_16.png", false));
rij.Items.Add(splitKnop);
Iconen als Embedded Resource opnemen
Voeg PNG-bestanden toe aan je project en stel hun Build Action in op Embedded Resource. Zo worden ze meegecompileerd in de DLL en heb je geen losse bestanden nodig tijdens de installatie.
In het .csproj-bestand zie je dan:
<ItemGroup>
<EmbeddedResource Include="Resourceslokken_32.png" />
<EmbeddedResource Include="Resources\pdf_16.png" />
</ItemGroup>
Veelgemaakte fouten
Tab verschijnt niet na workspace-switch — AutoCAD vernieuwt het lint bij elke workspace-load. Luister naar ComponentManager.ItemInitialized en controleer op het RibbonControl-type.
Dubbele tabs bij herinitialisatie — controleer altijd of de tab al bestaat (ribbon.Tabs.FirstOrDefault(t => t.Id == ...)) en verwijder hem vóór je hem opnieuw toevoegt.
Icoon is null — controleer de naam van de embedded resource. De naam is Namespace.Map.NaamVanBestand.png met puntjes in plaats van slashes.
Samenvatting
Een ribbon-tab geeft je add-in een professionele plek in het AutoCAD-lint. Zorg dat je luistert naar workspace-events voor persistentie, gebruik embedded resources voor iconen, en implementeer een nette ICommand handler om commando's te delegeren naar de AutoCAD-commandoregel.
Comments
No comments yet — be the first!
Leave a comment
Sign in to skip moderation — anonymous comments are reviewed before appearing.