Aller au contenu

Nombre de références dans une infobulle


(gile)

Messages recommandés

Salut,

 

Une petite application qui affiche le nombre de références dans le dessin du bloc survolé par le curseur.

 

BlockCountToolTip.zip contient un dossier BlockCountToolTip.bundle à utiliser avec la fonctionnalité AutoLoader (pour les versions 2012 et ultérieures) qu'il suffit de placer dans le répertoire suivant (copier le chemin dans la barre d'adresse) pour que l'application soit automatiquement chargée à chaque lancement d'AutoCAD :

%appdata%\Autodesk\ApplicationPlugins\

Pour les version 2010, 2011 il faudra charger BlockCountToolTip_18.dll avec NETLOAD ou enregistrer l'application dans la base de registre.

 

Le code C#

// (C) Copyright 2012 by Gilles Chanteau 
//
using System;
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.Runtime;
using AcAp = Autodesk.AutoCAD.ApplicationServices.Application;

[assembly: ExtensionApplication(typeof(Gile.BlockCountExtensionApplication.BlockCountToolTip))]

namespace Gile.BlockCountExtensionApplication
{
   public class BlockCountToolTip : IExtensionApplication
   {
       private static DocumentCollection docs;
       private static RXClass blockRefClass;

       public void Initialize()
       {
           docs = AcAp.DocumentManager;
           blockRefClass = RXClass.GetClass(typeof(BlockReference));
           docs.DocumentCreated += onDocumentCreated;
           docs.DocumentToBeDestroyed += onDocumentToBeDestroyed;
           foreach (Document doc in docs)
           {
               doc.Editor.PointMonitor += onPointMonitor;
           }
       }

       public void Terminate() { }

       void onDocumentCreated(object sender, DocumentCollectionEventArgs e)
       {
           if (e.Document != null)
               e.Document.Editor.PointMonitor += onPointMonitor;
       }

       void onDocumentToBeDestroyed(object sender, DocumentCollectionEventArgs e)
       {
           if (e.Document != null)
               e.Document.Editor.PointMonitor -= onPointMonitor;
       }

       void onPointMonitor(object sender, PointMonitorEventArgs e)
       {
           if ((e.Context.History & PointHistoryBits.FromKeyboard) == PointHistoryBits.FromKeyboard)
               return;

           FullSubentityPath[] paths = e.Context.GetPickedEntities();

           if (paths == null || paths.Length == 0)
               return;

           ObjectId[] ids = paths[0].GetObjectIds();

           if (ids == null || ids.Length == 0)
               return;

           ObjectId id = ids[0];

           if (id.IsValid && id.ObjectClass == blockRefClass)
           {
               Database db = id.Database;
               int cnt = 0;
               using (Transaction tr = db.TransactionManager.StartOpenCloseTransaction())
               {
                   BlockReference br = (BlockReference)tr.GetObject(id, OpenMode.ForRead);
                   bool isDyn = br.IsDynamicBlock;
                   BlockTableRecord btr = isDyn ?
                       (BlockTableRecord)tr.GetObject(br.DynamicBlockTableRecord, OpenMode.ForRead) :
                       (BlockTableRecord)tr.GetObject(br.BlockTableRecord, OpenMode.ForRead);
                   string name = btr.Name;
                   ObjectId cSpaceId = db.CurrentSpaceId;
                   foreach (ObjectId brId in btr.GetBlockReferenceIds(true, false))
                   {
                       DBObject bRef = tr.GetObject(brId, OpenMode.ForRead);
                       if (bRef.OwnerId == cSpaceId)
                           cnt++;
                   }
                   if (isDyn)
                   {
                       foreach (ObjectId anonId in btr.GetAnonymousBlockIds())
                       {
                           BlockTableRecord anonBtr = (BlockTableRecord)tr.GetObject(anonId, OpenMode.ForRead);
                           foreach (ObjectId brId in anonBtr.GetBlockReferenceIds(true, false))
                           {
                               DBObject bRef = tr.GetObject(brId, OpenMode.ForRead);
                               if (bRef.OwnerId == cSpaceId)
                                   cnt++;
                           }
                       }
                   }
                   e.AppendToolTipText(String.Format("'{0}' {1}\n{2} référence{3}\n",
                       btr.Name,
                       isDyn ? "(dynamique)" : "",
                       cnt,
                       cnt > 1 ? "s" : ""));
                   tr.Commit();
               }
           }
       }
   }
}

 

L'équivalent F#

// (C) Copyright 2012 by Gilles Chanteau 
//
module Gile.BlockCount

open System
open Autodesk.AutoCAD.ApplicationServices
open Autodesk.AutoCAD.DatabaseServices
open Autodesk.AutoCAD.EditorInput
open Autodesk.AutoCAD.Runtime

let docMan = Application.DocumentManager
let blkRefClass = RXClass.GetClass(typeof<BlockReference>)

type BCountToolTip() =
   let pointMonitor (e: PointMonitorEventArgs) =
       if (e.Context.History &&& PointHistoryBits.FromKeyboard) <> PointHistoryBits.FromKeyboard then
           let paths = e.Context.GetPickedEntities()
           if paths <> null && paths.Length > 0 then
               let ids = paths.[0].GetObjectIds()
               if ids <> null && ids.Length > 0 then
                   let id  = ids.[0]
                   if id.IsValid && id.ObjectClass = blkRefClass then
                       let db = id.Database
                       let spaceId = db.CurrentSpaceId
                       use tr = db.TransactionManager.StartOpenCloseTransaction()

                       let countRefs (btr: BlockTableRecord) =
                           btr.GetBlockReferenceIds(true, false)
                           |> Seq.cast
                           |> Seq.filter(fun id -> tr.GetObject(id, OpenMode.ForRead).OwnerId = spaceId)
                           |> Seq.length

                       let br = tr.GetObject(id, OpenMode.ForRead) :?> BlockReference
                       let isDyn = br.IsDynamicBlock
                       let btrId = if isDyn then br.DynamicBlockTableRecord else br.BlockTableRecord
                       let btr = tr.GetObject(btrId, OpenMode.ForRead) :?> BlockTableRecord
                       let cnt = 
                           countRefs btr + 
                           if isDyn then
                               seq { for id in btr.GetAnonymousBlockIds() ->
                                       tr.GetObject(id, OpenMode.ForRead) :?> BlockTableRecord |> countRefs }
                               |> Seq.sum
                           else 0
                       e.AppendToolTipText(String.Format("'{0}' {1}\n{2} référence{3}\n", 
                                                           btr.Name, 
                                                           (if isDyn then "(dynamique)" else ""),
                                                           cnt,
                                                           if cnt > 1 then "s" else ""))
                       tr.Commit()

   interface IExtensionApplication with
       member x.Initialize() = 
           docMan.DocumentCreated.Add (fun e ->
               if e <> null then
                   e.Document.Editor.PointMonitor.Add pointMonitor)
           for doc in docMan |> Seq.cast<Document> do
               doc.Editor.PointMonitor.Add pointMonitor
       member x.Terminate() = ()

[<assembly: ExtensionApplication(typeof<BCountToolTip>)>]
do()

Gilles Chanteau - gileCAD -
Développements sur mesure pour AutoCAD
ADSK_Expert_Elite_Icon_S_Color_Blk_125.png

Lien vers le commentaire
Partager sur d’autres sites

Salut Gilles,

 

Le plugin ne se charge pas, il créé un fichier log qui contient:

 

 

--- Module d'application ---

Version de schéma=

Version de l'app.=

Nom=

Description=

Créateur=

Code produit=

Icône=

Fichier d'aide=

Documentation en ligne=

Recharger menu?=0

 

--- Composants d'exécution requis ---

SE= Min. série= Max. série= Plateforme=

 

Chemin de support=

Chemin de palette d'outils=

Code d'erreur=0

--- Détails de la société ---

Nom de la société=

Téléphone=

URL de la société=

E-mail de la société=

Lien vers le commentaire
Partager sur d’autres sites

J'ai enlevé les caractères accentués dans PackageContents.xml et ça va tout de suite mieux...Ca marche.

 

Le nombre de références est celui dans la présentation courante ou dans le dessin?

 

Suggestion: ajouter un saut de ligne ou un caractère de séparation après le message dans l'info bulle car il y a parfois d'autres messages qui viennent se coller au tient et c'est pas très lisible.

Lien vers le commentaire
Partager sur d’autres sites

Merci Patrick pour ce retour.

 

J'ai corrigé l'encodage du fichier PackageContents.xml, il ne devrait plus y avoir de problèmes avec les caractères accentués. J'ai aussi ajouté un saut de ligne après le message. Le téléchargement est mis à jour.

 

J'avais oublié de préciser : le nombre de références correspond à celui des références directement insérées dans l'espace courant (objet ou papier). Les références insérées dans les autres espaces ou imbriquées dans des blocs ne sont donc pas comptées.

Gilles Chanteau - gileCAD -
Développements sur mesure pour AutoCAD
ADSK_Expert_Elite_Icon_S_Color_Blk_125.png

Lien vers le commentaire
Partager sur d’autres sites

Créer un compte ou se connecter pour commenter

Vous devez être membre afin de pouvoir déposer un commentaire

Créer un compte

Créez un compte sur notre communauté. C’est facile !

Créer un nouveau compte

Se connecter

Vous avez déjà un compte ? Connectez-vous ici.

Connectez-vous maintenant
×
×
  • Créer...

Information importante

Nous avons placé des cookies sur votre appareil pour aider à améliorer ce site. Vous pouvez choisir d’ajuster vos paramètres de cookie, sinon nous supposerons que vous êtes d’accord pour continuer. Politique de confidentialité