This article describes how to implement a local load model. Before reading this blog, I need to refer to another blog post on Dynamic Loading Model: http://www.cnblogs.com/enjoyeclipse/archive/2012/03/21/2410439.html
1. Effect:
Because the whole sand table scenario is too large, it is necessary to load and enlarge the pier. I don't know if you have ever played real-time football. This is the result if you select a player.
2. Ideas:
1) First, construct a container with the ViewPort element;
2) select the desired local model from the dashboard andClone a copy (Because of the Tree relationship of model Objects in WPF, you cannot directly Add (model). You must Add (model. Clone ()),
3) Add the local model to the container's ViewPort.
3. Implementation:
1) First, construct a container with the ViewPort element.
Create a container (UserControl): PartModelControl. The most important thing is to include the ViewPort, and set the light, camera, and so on in advance.
The xaml code is as follows:
<UserControl x: Class = "UI. Common. UserControls. PartModelControl"
Xmlns = "http://schemas.microsoft.com/winfx/2006/xaml/presentation"
Xmlns: x = "http://schemas.microsoft.com/winfx/2006/xaml" xmlns: converter = "clr-namespace: UI. Common. Converters"
Background = "Transparent"
SnapsToDevicePixels = "True"
X: Name = "modelPartControl" PreviewMouseDoubleClick = "modelPartControl_MouseDoubleClick">
....
<Viewport3D x: Name = "_ partViewPort">
<Viewport3D. Camera>
<! -- <PerspectiveCamera x: Name = "camera" FieldOfView = "45" FarPlaneDistance = "1782.5084757839907" LookDirection = "607.743292014972,-0.1" NearPlaneDistance = "0.0207443237299856" Position =, -2.1316282072803E-14,407.743292014972 "UpDirection =", 0 "/> -->
<PerspectiveCamera x: Name = "camera" FieldOfView = "30" FarPlaneDistance = "102122.68952517369" LookDirection = "292.292480468755,-0.00048828125,-2204.4668208912" Position = "-292.292480468755, 0.00048828125, 2204.4668208912 "NearPlaneDistance =" 0.1 "UpDirection =", 0 "/>
</Viewport3D. Camera>
<ModelVisual3D x: Name = "World">
<ModelVisual3D x: Name = "AmbientLightContainer">
<ModelVisual3D. Content>
<AmbientLight x: Name = "AmbientLight" Color = "# FF7F7F7F"/>
</ModelVisual3D. Content>
</ModelVisual3D>
<ModelVisual3D x: Name = "DirectionalLightContainer">
<ModelVisual3D. Content>
<DirectionalLight x: Name = "DirectionalLight" Color = "# FF3F3F3F" Direction = "0, 0,-1">
<DirectionalLight. Transform>
<TranslateTransform3D OffsetX = "0" OffsetY = "0" OffsetZ = "3"/>
</DirectionalLight. Transform>
</DirectionalLight>
</ModelVisual3D. Content>
</ModelVisual3D>
<ModelVisual3D. Transform>
<TranslateTransform3D x: Name = "transform" OffsetX = "0" OffsetY = "0" OffsetZ = "0"/>
</ModelVisual3D. Transform>
</ModelVisual3D>
</Viewport3D>
<! -- END Viewport -->
....
</UserControl>
2) select the desired local model from the dashboard andClone one copy
- Select a model from the sand table: First, you cannot use the default WPF method to create a 3D model. You must use the third-party database WaveFrontObjLoader to dynamically load the model, because at this time, the 3D name and model will form a Dictionary, you can use the Find (string Name) method to load the model. For more information, see my blog: http://www.cnblogs.com/enjoyeclipse/archive/2012/03/21/2410439.html
- To Clone ModelVisual3DWithName:
[ContentProperty ("Children")]
Public class ModelVisual3DWithName: ModelVisual3D, ICloneable
{
Public string Name {get; set ;}
Public object Tag {get; set ;}
Public object Clone ()
{
Var model = new ModelVisual3DWithName {Content = Content. Clone (),
Name = Name,
Tag = Tag
};
Model. SetColor (Brushes. DefaultSectionBrush );
Return model;
}
Public void SetMaterial (Material material)
{
Var geometrymodel = Content as GeometryModel3D;
If (geometrymodel! = Null)
{
Geometrymodel. Material = material;
}
Else
{
}
}
Public Material GetMaterial ()
{
Var geometrymodel = Content as GeometryModel3D;
If (geometrymodel = null)
{
Return null;
}
Return geometrymodel. Material;
}
Public void SetColor (Brush color)
{
Var geometrymodel = Content as GeometryModel3D;
If (geometrymodel. Material is MaterialGroup)
{
Var materialGroup = geometrymodel. Material as MaterialGroup;
SetMaterialGroupColor (materialGroup, color );
}
Else
{
DiffuseMaterial material = geometrymodel. Material as DiffuseMaterial;
If (material! = Null &&! Material. IsFrozen)
{
Material. Brush = color;
}
}
}
Private void SetMaterialGroupColor (MaterialGroup materialGroup, Brush color)
{
Foreach (var groupItem in materialGroup. Children)
{
If (groupItem is DiffuseMaterial &&! GroupItem. IsFrozen)
{
Var tmpItem = groupItem as DiffuseMaterial;
TmpItem. Brush = color;
}
}
}
}
3) Add the cloned model to the container.
Call the world. children. Add () method to Add the model to the container. The logic is as follows:
Var findModel = _ baseModel. Find (modelName) as ModelVisual3DWithName;
If (findModel! = Null)
{
Model. Children. Add (findModel. Clone () as ModelVisual3DWithName );
}
World. Children. Add (findModel );