ArcObjects (ArcGIS for Desktop ja C #): Kuinka suoratoistaa ArcMap COM -käyttöliittymän ja mukautettujen .Net UserControl -objektien välillä?

Luon apuohjelman suoritettavaksi ArcGIS for Desktopissa käyttämällä ArcObjectsia (9.3.1 SDK) ja C # .Netiä. Prototyyppini sisältää työkalurivin, jossa on kaksi yhdistelmäruudut ja työkalu. Ensimmäinen yhdistelmä valitsee tason TOC: ssä ja toinen valitsee kentän valitusta tasosta. Työkalua käytetään vuorovaikutuksessa kartan kanssa.

Haluan periaatteessa valita valitse kelvollinen kenttä, napsauta sitten kartalla olevaa ominaisuutta ja hae sen arvo valitulle kentälle. Tässä on työkalupalkin kuva, jos se auttaa:

kirjoita kuvan kuvaus tähän

[kysymys on lähes kokonaan muotoiltu täältä alas]

Minun ongelmani on tilan siirtäminen alkuperäisten COM-käyttöliittymän osien ja mukautettujen .Net-ohjaimien välillä. Haluan esimerkiksi saada kiinni DropDownClosed-tapahtuma Taso-yhdistelmäruudusta, koota kelvollinen sarakeluettelo kyseiseen tasoon nähden ja käyttää kenttänimiluetteloa (IFields: n kautta) Kentät-yhdistelmäruutuun.

Kun soveltamalla joitain RagiYaserBurhamin ja blah238: n alkuperäisiä kommentteja ja yhdistämällä ne tämän sivun yksityiskohtiin, seuraava DropDownClosed-tapahtumankäsittelijä siirtyy yhdistelmäruudusta takaisin työkalupalkkiin ( ICommandBar), mutta en ymmärrä miten lähetetään ICommandItemistä takaisin Fields-yhdistelmäruudun käyttöönottoon UserControlissa:

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); } 

Joten .. nyt Olen täällä .. kuinka voin heittää kentät Kohde FieldSelectUC: een?

[ Ratkaisu ]

Kuten blah238 ehdotti, yritin lähettää ICommandItem.Command mukautettuun UserControl-toteutukseeni ja se teki temppun.

Ensin minun piti lisätä julkinen lisenssi FieldSelectUC UserControl -laitteeseen palauttamaan viittauksen ComboBoxiin; tuo yksinkertainen käyttöoikeus näyttää tältä:

// fieldSelectCBO is the name of the combobox control in the design view.. public ComboBox FieldsComboBox { get { return fieldSelectCBO; } } 

Kun muutos on paikallaan, tässä on DropDownClosed-tapahtumankäsittelijä, joka täyttää Fields-yhdistelmäruudun kaikilla kentillä. valittu taso:

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!"); } } 

Tämä on edelleen likainen testipenkki (siis AngryToolbar). Mutta ratkaisu näyttää, miten aloittaa laajennetusta UserControlista, joka toteuttaa ICommandin ja IToolControlin ja poraa takaisin .Net-komponenttiin. Arvostan todella kaikkien ehdotuksia tarjoaneiden henkilöiden apua. Kiitos paljon. 🙂

Kommentit

  • Kuinka siitä, miten muutat layerName-muuttujan julkiseksi staattiseksi ulottuvuudeksi?
  • @ artwork21, se kuulostaa hyvältä, mutta en ’ ole vieläkään varma, kuinka pääsen kummankin yhdistelmäruudun ilmentymään sen vastaavuus työkalupalkissa? Tiedätkö mitä tarkoitan? Epäilen sen olevan ’ yksinkertainen olennainen asia, josta en ’ m ole vain tietoinen.
  • Tämä kuulostaa erolta kysymys. En ’ ole varma, miksi sinun on tehtävä se. Minusta tuntuu, että Fields-yhdistelmäruutu on tyhjennettävä ja täytettävä uudelleen Layer-yhdistelmän perusteella. Tason yhdistelmäruutu tulee täyttää asiakirjatapahtumien kuuntelijan perusteella.
  • @RichWawrzonek, mikä on aivan oikein. Mutta en ’ ole varma, kuinka päästä Kentät-yhdistelmän olemassa olevaan esiintymään Tasot-yhdistelmästä. Tätä varten työkalun on luettava molemmat arvot.

vastaus

Kuten ymmärrän, sinulla on kaksi .NET ComboBoxia UserControlissa, joka toteuttaa ICommandia ja IToolControlia, ja haluat saada viitteen yhdestä yhdistelmäruudusta toisesta. Niin kauan kuin ne ovat samassa laajuudessa, sinun pitäisi vain pystyä viittaamaan niihin muuttujien nimillä (tarkista UserControl-suunnittelijalta ohjainten nimet).

Jos kaksi yhdistelmäruutua ovat erillisinä UserControls ja yritä sitten lähettää ICommandItem.Command toiseen UserControlisi.

Katso esimerkki 9.3-ohjeesta tästä esimerkistä: Viimeksi käytetyt tiedostot – komento, MultiItem ja ToolControl

Tässä on myös ESRI-foorumin viesti, jossa keskustellaan tästä asiasta: http://forums.esri.com/Thread.asp?c=93&f=993&t=170088

Kommentit

  • Bingo. Tämä rivi teki tempun saadakseen ICommandItem -esiintymästä takaisin toteutettuun UserControl -luokkaan: FieldSelectUC fs = fieldsItem.Command as FieldSelectUC; Näen nyt kaikki sen ’ rekvisiittaa virheenkorjaimessa. Valtava kiitos sinulle.
  • Hurraa! Olen ’ käyttänyt lisäosia yksinomaan jonkin aikaa, joten minun piti kaivaa läpi vanhoja juttuja muistaakseni, miten kaikki toimi 🙂 Tällainen asia on paljon helpompaa (tosin tosin tosin vähemmän joustava) 10-apuohjelmilla, koska on olemassa tietty ComboBox-tyyppi ja voit vain viitata muihin lisäosakomponenteihin, joissa on staattisia muuttujia ja menetelmiä.
  • Kyllä, se tuntui varmasti helpommalta uusien apuohjelmien kautta. Tutkiessani tätä löysin tämän ja sen lisäosat, mutta ’ ne eivät vain olleet toteutukseni käytettävissä. .Net-ohjeessa oleva esimerkki GraphicsLayerToolControlista (järjestelmässäni osoite on C:\Program Files (x86)\ArcGIS\DeveloperKit\SamplesNET\Desktop\GraphicsLayerToolControl\CSharp\GraphicsLayerToolControl2008.sln), joka auttoi minua pääsemään UserControlin ja tapahtumien kanssa, mutta en vain voinut ’ t selvitä kuinka lyödä reikä .Netiin COM-ohjaimesta. En voi ’ liioitella, kuinka kiitollinen olen. Ystävällisin terveisin.

Vastaa

Aina kun teen tällaista, talletan kerrosten ja kenttien nimet staattiseen työkalurivin sisältämä ominaisuusjoukko. Sitten käytän asiakirjatapahtumien käsittelijää tarkistamaan, onko kerroksia lisätty / poistettu ArcMapista tai onko asiakirjaa muutettu. Tason ja kentän ominaisuudet päivittyvät aina, kun käyttäjä muuttaa niitä avattavassa valikossa. Jos taso poistetaan ArcMapista tai asiakirja suljetaan, ne nollataan. Sitten voit vain tarkistaa nolla-arvot ennen ohjelman suorittamista.

Hanki viittaus yhdistelmäruutuun ICommandItem-käyttöliittymän kautta:

ICommandItem toolbar = _iApp.Document.CommandBars.Find (”ArcProject.UI.AngryToolbar”, false, false);
ICommandItem fieldsItem = (työkalurivi kuten ICommandBar) .Find (”ArcProject.UI.FieldSelectUC”, epätosi); IComboBox cbo = (IComboBox) kentätItem; // Tarvitsee viitteen ESRI.ArcGIS.SystemUI;

kommentit

  • +1, jotta saat sen kuulostamaan niin helpolta. 🙂 Mutta minulla on ongelmana käyttää jo ennennäkemättömän ohjaimen ominaisuuksia minkä tahansa muun ohjaimen näkökulmasta. Pidän ajatuksestasi heidän jaettujen ominaisuuksiensa sijoittamisesta työkalupalkkiin. Voisitko päivittää vastauksesi osoittamaan, kuinka voin todella lukea sisältävän työkalurivin ominaisuudet yhden yhdistelmäruudun näkökulmasta? ’ Koska ’ on periaatteessa mitä ’ m jälkeen. Tiedän jo, kuinka asiakirjatapahtumien avulla voi kuunnella muutoksia TOC: hen, joten en tarvitse ’ tarvetta apua tässä asiassa. Kiitos vastauksestasi.
  • @elrobis Voit myös laittaa jaetun tilan itse ICommandiin (koska aina on vain yksi esiintymä) ja pyytää sitten ohjaimia saamaan komennon komentoon help.arcgis.com/fi/sdk/10.0/arcobjects_net/componenthelp/…
  • Ragi on oikein. Koska käytät COM-työkaluriviä, voit lähettää yhdistelmäruudun uid: n ICommandBar.Find-menetelmälle saadaksesi viitteen. Hänen linkkinsä selittää kaiken.
  • Pidän myös Ragi ’ -ideasta. Minulta puuttuu kuitenkin jotain perustavaa laatua olevaa. Esimerkiksi tämä rivi palauttaa tyhjän työkalupalkin (jossa this on UserControl tunnisteella ja yhdistelmäruudulla): ICommandBar toolbar = this.Parent as ICommandBar; Se ’ on tällainen olennainen käyttöliittymäobjekti, joka tappaa minut. En tiedä, ’ miten palata työkaluriville kumman tahansa ehdotuksen toteuttamiseksi. (Ja pidän itse asiassa näiden työkalupalkin ideoista hieman paremmin. ’ d luultavasti teen sen lisäämällä julkisen getterin työkalupalkkiin, joka käyttää Ragi ’ idea). Kiitos jatkuvasta avusta.
  • En ’ usko, että this.Parent on kelvollinen COM-liitännöille – eli .NET / Windows Forms -konsepti. Et ’ et halua ” kulkea käyttöliittymän läpi ”, haluat käyttää ICkomennot tunnusten mukaan.

Vastaa

Minulla oli samanlainen ongelma mukautetun työkalun kanssa. Minulla on mukautettu lomake, joka avautuu painikkeella AddIn-työkalupalkissa ArcGis 10.x: ssä. Tällä lomakkeella on painike, jonka pitäisi palauttaa napsautuksen koordinaatit kartalla napsauttamalla. Voisin käynnistää työkalun ja käsitellä napsautusta kartalla, mutta en voinut palauttaa arvoa takaisin lomakkeeseeni, koska muokkaustyökaluun lähetys epäonnistui aina. Ratkaisuna oli käyttää AddIn-tiedostoa ESRI.ArcGIS.Desktop.AddIns-tiedostosta. Tämän avulla oli helppo päästä käyttämään mukautetun työkalun jokaista omaisuutta ja metodia. ESRI-dokumentaatio on täällä: http://resources.arcgis.com/en/help/arcobjects-net/conceptualhelp/index.html#/Add_in_coding_patterns/0001000000zz000000/

Tässä on koodinpätkä OnClick- Mukautetun lomakkeen painikkeen tapahtuma:

//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; 

Vastaa

Sähköpostiosoitettasi ei julkaista. Pakolliset kentät on merkitty *