Létrehozok egy segédprogramot az ArcGIS for Desktop futtatásához ArcObjects (9.3.1 SDK) és C # .Net használatával. A prototípusom egy eszköztárat tartalmaz két comboboxok és egy eszköz. Az első kombó kiválaszt egy réteget a TOC-ben, a második pedig egy mezőt a kiválasztott rétegből. Az eszközt a térképpel való interakcióra használják.
Alapvetően egy réteget, válasszon ki egy érvényes mezőt, majd kattintson egy elemre a térképen, és szerezze be annak értékét a kiválasztott mező számára. Itt van egy kép az eszköztárról, ha az segít:
[a kérdés szinte teljesen át van formázva innen lefelé]
A problémám az állapot átvitele a natív COM felhasználói felület részei és az egyéni .Net vezérlők között. Például el akarom fogni a DropDownClosed eseményt a Layer kombinációs dobozon, összeállít egy érvényes oszloplistát a fóliához képest, majd alkalmazom a mezők nevének listáját (IFields-en keresztül) a Fields kombinációs dobozra. alkalmazva a RagiYaserBurham és a blah238 kezdeti megjegyzéseit, és egyesítve őket ezen oldal részleteivel, a következő DropDownClosed eseménykezelő a comboboxból visszamegy az eszköztárba ( ICommandBar), de nem értem, hogyan lehet átküldeni az ICommandItem-ről a Fields combobox implementációjához egy UserControl-ban:
private void layerSelectCBO_DropDownClosed(object sender, EventArgs e) { _completionNotify.SetComplete(); string layerName = (sender as ComboBox).SelectedItem as string; // These two lines are a combination of initial commenter suggestions. ICommandItem toolbar = _iApp.Document.CommandBars.Find("ArcProject.UI.AngryToolbar", false, false); ICommandItem fieldsItem = (toolbar as ICommandBar).Find("ArcProject.UI.FieldSelectUC", false); }
Tehát .. most Itt vagyok .. hogyan vethetem a FieldItem elemet a FieldSelectUC fájlba?
[ A megoldás ]
Ahogy a blah238 javasolta, megpróbáltam átküldeni az ICommandItem.Command-ot az egyedi UserControl implementációmnak, és ez megcsinálta a trükköt.
Először hozzá kellett adnom egy nyilvános hozzáférést a FieldSelectUC
UserControl-hoz, hogy visszatérést adjak a ComboBox-ba; ez az egyszerű hozzáférés így néz ki:
// fieldSelectCBO is the name of the combobox control in the design view.. public ComboBox FieldsComboBox { get { return fieldSelectCBO; } }
Ha ez a módosítás helyben van, akkor itt egy DropDownClosed eseménykezelő, amely feltölti a Fields comboboxot a kiválasztott réteg:
private void layerSelectCBO_DropDownClosed(object sender, EventArgs e) { _completionNotify.SetComplete(); string layerName = (sender as ComboBox).SelectedItem as string; // get the toolbar.. ICommandItem toolbar = _iApp.Document.CommandBars.Find("ArcProject.UI.AngryToolbar", false, false); // get my fields combo by way of CommandItem.Command.. ICommandItem fieldsCI = (toolbar as ICommandBar).Find("ArcProject.UI.FieldSelectUC", false); FieldSelectUC fieldsUC = fieldsCI.Command as FieldSelectUC; ComboBox fieldsComboBox = fieldsUC.FieldsComboBox; // get the fields for the selected layer.. IFields fields = null; int layerCount = _iDoc.FocusMap.LayerCount; int i; for (i = 0; i < layerCount; i++) { if (_iDoc.FocusMap.get_Layer(i).Name == layerName) { if (_iDoc.FocusMap.get_Layer(i) is FeatureLayer) { fields = (_iDoc.FocusMap.get_Layer(i) as FeatureLayer).FeatureClass.Fields; } } } // Build a list of field names for the combobox items.. List<string> fieldNameList = new List<string>(); if (fields != null) { int fieldCount = fields.FieldCount; int j; for (j = 0; j < fieldCount; j++) { string oneFieldName = fields.get_Field(j).Name; fieldNameList.Add(oneFieldName); } } // Populate the combobox items.. if (fieldNameList.Count > 0) { fieldsComboBox.Items.Clear(); foreach (string fieldName in fieldNameList) { fieldsComboBox.Items.Add(fieldName); } fieldsComboBox.SelectedItem = fieldsComboBox.Items[0]; } else { fieldsComboBox.Items.Add("Error: No fields!"); } }
Ez még mindig piszkos tesztasztal (tehát az AngryToolbar). De a megoldás megmutatja, hogyan lehet elindulni egy kiterjesztett UserControl-ból, amely az ICommand és az IToolControl és térjen vissza egy .Net komponensre. Nagyon értékelem mindenki segítségét, aki javaslatokat tett. Köszönöm szépen. 🙂
Megjegyzések
- Hogyan arról, hogy a layerName változó nyilvános, statikus hatókörűvé válik-e?
- @ artwork21, ez jól hangzik, de még mindig nem vagyok biztos abban, id = “f9316bd63b”>
megfelelője az eszköztáron? Tudja, mire gondolok? Gyanítom, hogy ‘ egy egyszerű alapvető dolog, amiről én ‘ nem tudok.
Válasz
Mint megértettem, két .NET ComboBox van egy UserControl-on, amely az ICommand és az IToolControl végrehajtását végzi, és hivatkozást szeretne kapni az egyik kombinációs mezőre a másiktól. Amíg ugyanabban a körben vannak, csak a változó nevükön kell hivatkozni rájuk (ellenőrizze a kezelőszervek nevét a UserControl tervezőjében).
Ha a két kombinációs mező külön van UserControls, majd próbálja átküldeni az ICommandItem.Command
elemet a másik UserControl parancsra.
Néhány példa: 9 div súgó: Legutóbb használt fájlok – Command, MultiItem és ToolControl
Itt található egy ESRI fórumbejegyzés is, amely a problémát tárgyalja: http://forums.esri.com/Thread.asp?c=93&f=993&t=170088
Megjegyzések
- Bingó. Ez a sor trükközött, hogy a
ICommandItem
példányból visszakerüljön az általam megvalósítottUserControl
osztályba:FieldSelectUC fs = fieldsItem.Command as FieldSelectUC;
Most már látom az összes ‘ kellékét a hibakeresőben. Óriási köszönet neked. - Hurrá! ‘ Egy ideje kizárólagosan használom a bővítményeket, ezért át kellett ásnom néhány régi dolgot, hogy emlékezzek az egész működésére 🙂 Ez a fajta dolog sokkal könnyebb (bár igaz kevésbé rugalmas) 10-es bővítményekkel, mivel létezik egy speciális ComboBox típus, és csak statikus változókkal és módszerekkel hivatkozhat más kiegészítő összetevőkre.
- Igen, az új kiegészítők révén mindenképpen könnyebbnek tűnt. Ennek kutatása során találtam ezt és azokat a bővítményeket, amelyek azonban csak ‘ nem elérhetőek a megvalósításom számára. A .Net súgóban szereplő GraphicsLayerToolControl példa (a rendszeremen ez a cím
C:\Program Files (x86)\ArcGIS\DeveloperKit\SamplesNET\Desktop\GraphicsLayerToolControl\CSharp\GraphicsLayerToolControl2008.sln
), amely segített elindulni a UserControl és események cuccai között, de ‘ ne találja ki, hogyan lehet a COM vezérlőből lyukat ütni a .Net felé. ‘ nem tudom eltúlozni, hogy mennyire hálás vagyok. Üdvözlettel.
Válasz
Valahányszor ilyesmit csinálok, a réteg és mező nevét statikusan tárolom az eszköztáron található tulajdonságkészlet. Ezután egy dokumentumesemény-kezelővel ellenőrizem, hogy vannak-e rétegek hozzáadva / eltávolítva az ArcMap-ból, vagy megváltozott-e a dokumentum. A réteg és a mező tulajdonságai frissülnek, amikor a felhasználó megváltoztatja azokat a legördülő menüben. Ha a fólia eltávolításra kerül az ArcMap-ból, vagy a dokumentum bezárul, akkor azok nullára lesznek állítva. Ezután csak ellenőrizheti a null értékeket, mielőtt a program fut.
Kérjen referenciát a comboboxra az ICommandItem felületen keresztül:
ICommandItem toolbar = _iApp.Document.CommandBars.Find (“ArcProject.UI.AngryToolbar”, false, false);
ICommandItem fieldsItem = (eszköztár mint ICommandBar) .Find (“ArcProject.UI.FieldSelectUC”, hamis); IComboBox cbo = (IComboBox) fieldsItem; // Hivatkozásra van szükség az ESRI.ArcGIS.SystemUI;
Megjegyzések
- +1 segítségével ilyen egyszerűen hangzik. 🙂 De az a problémám van, hogy bármilyen más vezérlés szempontjából hozzáférjek egy már példányos vezérlő tulajdonságaihoz. Tetszik az ötleted, miszerint a megosztott tulajdonságokat helyezik el az eszköztáron, frissítenéd a válaszodat, hogy megmutassam, hogyan tudom valójában elolvasni a benne lévő eszköztár tulajdonságait az egyik kombobox szempontjából? ‘ Mert ‘ alapvetően az, amit én ‘ m követek. Már tudom, hogyan kell használni a dokumentumeseményeket a TOC változásainak meghallgatásához, ezért nincs szükségem segítségre ebben a szempontban.
Köszönjük válaszát.
this
egy UserControl
címkével és komboboxmal): ICommandBar toolbar = this.Parent as ICommandBar;
Ez ‘ ez a fajta alapvető felhasználói felület objektum bejárása, amely megöl. Nem tudom, hogy ‘ hogyan juthatnék vissza az eszköztárra egyik javaslatod végrehajtásához. (És valójában egy kicsit jobban tetszik ezeknek a változatoknak az eszköztáron ötlete. Én ‘ d valószínűleg úgy teszem, hogy nyilvános gettert adok az eszköztárhoz, amely alkalmazza a Ragi ‘ s ötlet). Köszönöm a folyamatos segítséget. this.Parent
a COM interfészekre érvényes – vagyis .NET / Windows Forms koncepció. Nem ‘ nem akarja ” átmenni a felhasználói felületen “, hozzáférni szeretne a IC-parancsok azonosítójuk szerint. Válasz
Hasonló problémám volt egy egyéni eszközzel. Van egy egyéni űrlapom, amelyet az ArcGis 10.x AddIn-Eszköztárának egyik gombja nyit meg. Ezen az űrlapon található egy gomb, amelynek vissza kell kapnia egy kattintás koordinátáit a térképen, bepattanva. Elindíthattam az eszközt, és kezelhettem a kattintást a térképen, de az értéket nem tudtam visszakapni az űrlapomhoz, mert az egyéni eszközre történő átküldés mindig nem sikerült. A megoldás az volt, hogy az ESRI.ArcGIS.Desktop.AddIns fájlt használja az AddIn használatával. Ezzel könnyű volt hozzáférni az egyedi eszköz minden tulajdonságához és metódusához. Az ESRI dokumentáció itt található: http://resources.arcgis.com/en/help/arcobjects-net/conceptualhelp/index.html#/Add_in_coding_patterns/0001000000zz000000/
Itt található az OnClick- A gomb eseménye az egyéni űrlapon:
//DESCRIPTION: //Connect a tool embedded in a Windows Form with the ArcGIS Application Framework. ESRI.ArcGIS.esriSystem.IUID UIDCls = new ESRI.ArcGIS.esriSystem.UIDClass(); UIDCls.Value = "MyNamespace_MyCustomTool"; IDocument actDoc = (IDocument)ArcMap.Document; //Finding the customTool ESRI.ArcGIS.Framework.ICommandItem commandItem = actDoc.CommandBars.Find(UIDCls, false, false); if (commandItem == null) { return; } //This cast would fail: //MyCustomTool_Class actCustomTool2 = (MyCustomTool_Class)commandItem.Command; MyCustomTool_Class actCustomTool = AddIn.FromID<MyCustomTool_Class (ThisAddIn.IDs.MyCustomTool); actCustomTool.actFrm = this; ArcMap.Application.CurrentTool = commandItem;