protected override void OnClick() { // find footprint layer var buildingLyr = MapView.Active.Map.GetLayersAsFlattenedList().FirstOrDefault(l => l.Name == "BuildingStructure") as FeatureLayer; if (buildingLyr == null) { MessageBox.Show("Can't find layer: BuildingStructure"); return; } // create new structural features _ = QueuedTask.Run(() => { // get all selected lines and use them as the building footprint var bldgSelection = buildingLyr.GetSelection(); Multipatch mp = null; #region Get MultiPatch foreach (var footprintOid in bldgSelection.GetObjectIDs()) { // get the multipatch shape using the Inspector var insp = new Inspector(); insp.Load(buildingLyr, footprintOid); mp = insp.Shape.Clone() as Multipatch; break; } #endregion if (mp == null) { MessageBox.Show("No multipatch selected"); return; } // create a builder var mpb = new ArcGIS.Core.Geometry.MultipatchBuilderEx(mp); // apply the texture materials to the patches var patches = mpb.Patches; foreach (var patch in patches) { System.Diagnostics.Debug.WriteLine(patch.Material); MyMultipatchBuilder.ShowPatchLabels(patch); foreach (var coord in patch.TextureCoords2D) { System.Diagnostics.Debug.WriteLine($@"new Coordinate2D({coord.X},{coord.Y}),"); } break; } }); }
protected override async void OnClick() { #region Initialization // set up a set of TextureCoordinates - these determine how the texture is draped over a face // In this scenario we will use the same textureCoordinates for each face var textureCoords = new List <Coordinate2D>() { new Coordinate2D(4.67909908294678, -2.89953231811523), new Coordinate2D(-3.7085223197937, -2.89953231811523), new Coordinate2D(-3.6790623664856, 1.89953279495239), new Coordinate2D(4.67909908294678, -2.89953231811523), new Coordinate2D(-3.6790623664856, 1.89953279495239), new Coordinate2D(4.7085223197937, 1.89953327178955) }; esriTextureCompressionType compressionType = esriTextureCompressionType.CompressionJPEG; byte[] glassImageBuffer = GetBufferImage("pack://application:,,,/MultipatchBuilder;component/Textures/Glass.jpg", compressionType); var glassTextureResource = new TextureResource(new JPEGTexture(glassImageBuffer)); byte[] roofImageBuffer = GetBufferImage("pack://application:,,,/MultipatchBuilder;component/Textures/Roof.jpg", compressionType); var roofTextureResource = new TextureResource(new JPEGTexture(roofImageBuffer)); var materialGray = new BasicMaterial { Color = System.Windows.Media.Colors.Gray }; #endregion if (MapView.Active?.Map == null) { return; } // find footprint layer var footPrintLyr = MapView.Active.Map.GetLayersAsFlattenedList().FirstOrDefault(l => l.Name == "BuildingFootprints") as FeatureLayer; if (footPrintLyr == null) { MessageBox.Show("Can't find layer: BuildingFootprint"); return; } var buildingLyr = MapView.Active.Map.GetLayersAsFlattenedList().FirstOrDefault(l => l.Name == "BuildingStructure") as FeatureLayer; if (buildingLyr == null) { MessageBox.Show("Can't find layer: BuildingStructure"); return; } // create the multipatch var mpb = await QueuedTask.Run <MultipatchBuilderEx>(() => { // get all selected lines and use them as the building footprint var footPrintSelection = footPrintLyr.GetSelection(); Polygon footPrint = null; int floorLevels = 1; #region Get Footprint and Floor levels foreach (var footprintOid in footPrintSelection.GetObjectIDs()) { // get the multipatch shape using the Inspector var insp = new Inspector(); insp.Load(footPrintLyr, footprintOid); footPrint = GeometryEngine.Instance.ReverseOrientation(insp.Shape as Multipart) as Polygon; floorLevels = (int)insp["Floors"]; } if (footPrint == null) { MessageBox.Show("No selected building footprint found"); return(null); } #endregion // Create the MultipatchBuilder using the building footprints and the floorlevels as height return(MyMultipatchBuilder.CreateTriangleMultipatchBuilder(footPrint, floorLevels)); }); // apply texture or material // create a builder to work on the multipatch geometry switch (Module1.SelectedTexture) { case "Glass": // create the textures for walls and roof BasicMaterial glassMaterialTexture = new BasicMaterial { TextureResource = glassTextureResource }; BasicMaterial roofMaterialTexture = new BasicMaterial { TextureResource = roofTextureResource }; // apply the texture materials to the patches var patches = mpb.Patches; for (var iPatch = 0; iPatch < patches.Count; iPatch++) { if (iPatch == patches.Count - 1) { // roof patches[iPatch].Material = roofMaterialTexture; patches[iPatch].TextureCoords2D = textureCoords; } else { // walls patches[iPatch].Material = glassMaterialTexture; patches[iPatch].TextureCoords2D = textureCoords; } } break; case "Red-solid": // create some materials var materialRed = new BasicMaterial { Color = System.Windows.Media.Colors.Brown }; // apply the materials to the patches for (var iPatch = 0; iPatch < mpb.Patches.Count; iPatch++) { if (iPatch == mpb.Patches.Count - 1) { // roof mpb.Patches[iPatch].Material = materialGray; } else { // walls mpb.Patches[iPatch].Material = materialRed; } } break; case "Gray-solid": // create some materials var materialSilver = new BasicMaterial { Color = System.Windows.Media.Colors.Silver }; // apply the materials to the patches for (var iPatch = 0; iPatch < mpb.Patches.Count; iPatch++) { if (iPatch == mpb.Patches.Count - 1) { // roof mpb.Patches[iPatch].Material = materialGray; } else { // walls mpb.Patches[iPatch].Material = materialSilver; } } break; } // create a new feature using the multipatch bool result = await QueuedTask.Run(() => { // track the newly created objectID long newObjectID = -1; var op = new EditOperation { Name = "Create multipatch feature", SelectNewFeatures = false }; Module1.NewMultipatch = mpb.ToGeometry() as Multipatch; op.Create(buildingLyr, Module1.NewMultipatch, oid => newObjectID = oid); if (op.Execute()) { // save the oid in the module for other commands to use Module1.NewMultipatchOID = newObjectID; return(true); } var msg = op.ErrorMessage; return(false); }); }