LoadMeshes() public method

public LoadMeshes ( Renderer renderer, string path, Matrix4 transform, OpenTK.Vector4 tintColor, ValveResourceFormat.Package currentPackage = null, string skin = null ) : void
renderer GUI.Types.Renderer.Renderer
path string
transform Matrix4
tintColor OpenTK.Vector4
currentPackage ValveResourceFormat.Package
skin string
return void
Example #1
0
        private TabPage ProcessFile(string fileName, byte[] input, Package currentPackage)
        {
            var tab = new TabPage();

            if (fileName.EndsWith(".vpk", StringComparison.Ordinal))
            {
                var package = new Package();

                try
                {
                    if (input != null)
                    {
                        package.SetFileName(fileName);
                        package.Read(new MemoryStream(input));
                    }
                    else
                    {
                        package.Read(fileName);
                    }
                }
                catch (InvalidDataException) when(input == null && Regex.IsMatch(fileName, @"_[0-9]{3}\.vpk$"))
                {
                    // TODO: Update tab name
                    fileName = $"{fileName.Substring(0, fileName.Length - 8)}_dir.vpk";

                    package.Read(fileName);
                }

                // create a TreeView with search capabilities, register its events, and add it to the tab
                var treeViewWithSearch = new TreeViewWithSearchResults(ImageList)
                {
                    Dock = DockStyle.Fill,
                };
                treeViewWithSearch.InitializeTreeViewFromPackage("treeViewVpk", package);
                treeViewWithSearch.TreeNodeMouseDoubleClick += VPK_OpenFile;
                treeViewWithSearch.TreeNodeMouseClick       += VPK_OnClick;
                treeViewWithSearch.ListViewItemDoubleClick  += VPK_OpenFile;
                treeViewWithSearch.ListViewItemRightClick   += VPK_OnClick;
                tab.Controls.Add(treeViewWithSearch);

                // since we're in a separate thread, invoke to update the UI
                Invoke((MethodInvoker)(() => findToolStripButton.Enabled = true));
            }
            else if (fileName.EndsWith(".vcs", StringComparison.Ordinal))
            {
                var shader = new CompiledShader();

                var buffer = new StringWriter();
                var oldOut = Console.Out;
                Console.SetOut(buffer);

                if (input != null)
                {
                    shader.Read(fileName, new MemoryStream(input));
                }
                else
                {
                    shader.Read(fileName);
                }

                Console.SetOut(oldOut);

                var control = new TextBox();
                control.Font       = new Font(FontFamily.GenericMonospace, control.Font.Size);
                control.Text       = NormalizeLineEndings(buffer.ToString());
                control.Dock       = DockStyle.Fill;
                control.Multiline  = true;
                control.ReadOnly   = true;
                control.ScrollBars = ScrollBars.Both;
                tab.Controls.Add(control);
            }
            else
            {
                var resource = new Resource();
                if (input != null)
                {
                    resource.Read(new MemoryStream(input));
                }
                else
                {
                    resource.Read(fileName);
                }

                var resTabs = new TabControl
                {
                    Dock = DockStyle.Fill,
                };

                switch (resource.ResourceType)
                {
                case ResourceType.Texture:
                    var tab2 = new TabPage("TEXTURE")
                    {
                        AutoScroll = true,
                    };

                    try
                    {
                        var tex = (Texture)resource.Blocks[BlockType.DATA];

                        var control = new Forms.Texture
                        {
                            BackColor = Color.Black,
                        };
                        control.SetImage(tex.GenerateBitmap().ToBitmap(), Path.GetFileNameWithoutExtension(fileName), tex.Width, tex.Height);

                        tab2.Controls.Add(control);
                        Invoke(new ExportDel(AddToExport), $"Export {Path.GetFileName(fileName)} as an image", fileName, new ExportData {
                            Resource = resource
                        });
                    }
                    catch (Exception e)
                    {
                        var control = new TextBox
                        {
                            Dock      = DockStyle.Fill,
                            Font      = new Font(FontFamily.GenericMonospace, 8),
                            Multiline = true,
                            ReadOnly  = true,
                            Text      = e.ToString(),
                        };

                        tab2.Controls.Add(control);
                    }

                    resTabs.TabPages.Add(tab2);
                    break;

                case ResourceType.Panorama:
                    if (((Panorama)resource.Blocks[BlockType.DATA]).Names.Count > 0)
                    {
                        var nameTab     = new TabPage("PANORAMA NAMES");
                        var nameControl = new DataGridView
                        {
                            Dock                = DockStyle.Fill,
                            AutoSize            = true,
                            ReadOnly            = true,
                            AllowUserToAddRows  = false,
                            AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill,
                            DataSource          = new BindingSource(new BindingList <Panorama.NameEntry>(((Panorama)resource.Blocks[BlockType.DATA]).Names), null),
                        };
                        nameTab.Controls.Add(nameControl);
                        resTabs.TabPages.Add(nameTab);
                    }

                    break;

                case ResourceType.PanoramaLayout:
                    Invoke(new ExportDel(AddToExport), $"Export {Path.GetFileName(fileName)} as XML", fileName, new ExportData {
                        Resource = resource
                    });
                    break;

                case ResourceType.PanoramaScript:
                    Invoke(new ExportDel(AddToExport), $"Export {Path.GetFileName(fileName)} as JS", fileName, new ExportData {
                        Resource = resource
                    });
                    break;

                case ResourceType.PanoramaStyle:
                    Invoke(new ExportDel(AddToExport), $"Export {Path.GetFileName(fileName)} as CSS", fileName, new ExportData {
                        Resource = resource
                    });
                    break;

                case ResourceType.Sound:
                    var soundTab = new TabPage("SOUND");
                    var ap       = new AudioPlayer(resource, soundTab);
                    resTabs.TabPages.Add(soundTab);

                    Invoke(new ExportDel(AddToExport), $"Export {Path.GetFileName(fileName)} as {((Sound)resource.Blocks[BlockType.DATA]).Type}", fileName, new ExportData {
                        Resource = resource
                    });

                    break;

                case ResourceType.World:
                    var world   = new World(resource);
                    var worldmv = new Renderer(mainTabs, fileName, currentPackage, RenderSubject.World);
                    world.AddObjects(worldmv, fileName, currentPackage);

                    var worldmeshTab   = new TabPage("MAP");
                    var worldglControl = worldmv.CreateGL();
                    worldmeshTab.Controls.Add(worldglControl);
                    resTabs.TabPages.Add(worldmeshTab);
                    break;

                case ResourceType.WorldNode:
                    var node   = new WorldNode(resource);
                    var nodemv = new Renderer(mainTabs, fileName, currentPackage);
                    node.AddMeshes(nodemv, fileName, currentPackage);

                    var nodemeshTab   = new TabPage("MAP");
                    var nodeglControl = nodemv.CreateGL();
                    nodemeshTab.Controls.Add(nodeglControl);
                    resTabs.TabPages.Add(nodemeshTab);
                    break;

                case ResourceType.Model:
                    // Create model
                    var model = new Model(resource);

                    // Create skeleton
                    var skeleton = new Skeleton(resource);

                    // Create tab
                    var modelmeshTab = new TabPage("MESH");
                    var modelmv      = new Renderer(mainTabs, fileName, currentPackage, RenderSubject.Model);
                    model.LoadMeshes(modelmv, fileName, Matrix4.Identity, Vector4.One, currentPackage);

                    // Add skeleton to renderer
                    modelmv.SetSkeleton(skeleton);

                    // Add animations if available
                    var animGroupPaths = model.GetAnimationGroups();
                    foreach (var animGroupPath in animGroupPaths)
                    {
                        var animGroup = FileExtensions.LoadFileByAnyMeansNecessary(animGroupPath + "_c", fileName, currentPackage);

                        modelmv.AddAnimations(AnimationGroupLoader.LoadAnimationGroup(animGroup, fileName));
                    }

                    //Initialise OpenGL
                    var modelglControl = modelmv.CreateGL();
                    modelmeshTab.Controls.Add(modelglControl);
                    resTabs.TabPages.Add(modelmeshTab);
                    break;

                case ResourceType.Mesh:
                    if (!resource.Blocks.ContainsKey(BlockType.VBIB))
                    {
                        Console.WriteLine("Old style model, no VBIB!");
                        break;
                    }

                    var meshTab = new TabPage("MESH");
                    var mv      = new Renderer(mainTabs, fileName, currentPackage, RenderSubject.Model);

                    Invoke(new ExportDel(AddToExport), $"Export {Path.GetFileName(fileName)} as OBJ", fileName, new ExportData {
                        Resource = resource, Renderer = mv
                    });

                    mv.AddMeshObject(new MeshObject {
                        Resource = resource
                    });
                    var glControl = mv.CreateGL();
                    meshTab.Controls.Add(glControl);
                    resTabs.TabPages.Add(meshTab);
                    break;
                }

                foreach (var block in resource.Blocks)
                {
                    if (block.Key == BlockType.RERL)
                    {
                        var externalRefsTab = new TabPage("External Refs");

                        var externalRefs = new DataGridView
                        {
                            Dock = DockStyle.Fill,
                            AutoGenerateColumns = true,
                            AutoSize            = true,
                            ReadOnly            = true,
                            AllowUserToAddRows  = false,
                            AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill,
                            DataSource          = new BindingSource(new BindingList <ResourceExtRefList.ResourceReferenceInfo>(resource.ExternalReferences.ResourceRefInfoList), null),
                        };

                        externalRefsTab.Controls.Add(externalRefs);

                        resTabs.TabPages.Add(externalRefsTab);

                        continue;
                    }

                    if (block.Key == BlockType.NTRO)
                    {
                        if (((ResourceIntrospectionManifest)block.Value).ReferencedStructs.Count > 0)
                        {
                            var externalRefsTab = new TabPage("Introspection Manifest: Structs");

                            var externalRefs = new DataGridView
                            {
                                Dock = DockStyle.Fill,
                                AutoGenerateColumns = true,
                                AutoSize            = true,
                                ReadOnly            = true,
                                AllowUserToAddRows  = false,
                                AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill,
                                DataSource          = new BindingSource(new BindingList <ResourceIntrospectionManifest.ResourceDiskStruct>(((ResourceIntrospectionManifest)block.Value).ReferencedStructs), null),
                            };

                            externalRefsTab.Controls.Add(externalRefs);
                            resTabs.TabPages.Add(externalRefsTab);
                        }

                        if (((ResourceIntrospectionManifest)block.Value).ReferencedEnums.Count > 0)
                        {
                            var externalRefsTab = new TabPage("Introspection Manifest: Enums");
                            var externalRefs2   = new DataGridView
                            {
                                Dock = DockStyle.Fill,
                                AutoGenerateColumns = true,
                                AutoSize            = true,
                                ReadOnly            = true,
                                AllowUserToAddRows  = false,
                                AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill,
                                DataSource          = new BindingSource(new BindingList <ResourceIntrospectionManifest.ResourceDiskEnum>(((ResourceIntrospectionManifest)block.Value).ReferencedEnums), null),
                            };

                            externalRefsTab.Controls.Add(externalRefs2);
                            resTabs.TabPages.Add(externalRefsTab);
                        }

                        //continue;
                    }

                    var tab2    = new TabPage(block.Key.ToString());
                    var control = new TextBox();
                    control.Font = new Font(FontFamily.GenericMonospace, control.Font.Size);
                    try
                    {
                        if (block.Key == BlockType.DATA)
                        {
                            switch (resource.ResourceType)
                            {
                            case ResourceType.Particle:
                            case ResourceType.Mesh:
                                //Wrap it around a KV3File object to get the header.
                                control.Text = NormalizeLineEndings(new KV3File(((BinaryKV3)block.Value).Data).ToString());
                                break;

                            default:
                                control.Text = NormalizeLineEndings(block.Value.ToString());
                                break;
                            }
                        }
                        else
                        {
                            control.Text = NormalizeLineEndings(block.Value.ToString());
                        }
                    }
                    catch (Exception e)
                    {
                        control.Text = e.ToString();
                    }

                    control.Dock       = DockStyle.Fill;
                    control.Multiline  = true;
                    control.ReadOnly   = true;
                    control.ScrollBars = ScrollBars.Both;
                    tab2.Controls.Add(control);
                    resTabs.TabPages.Add(tab2);
                }

                tab.Controls.Add(resTabs);
            }

            return(tab);
        }
        internal void AddMeshes(Renderer.Renderer renderer, string path, Package package)
        {
            var data = Resource.Blocks[BlockType.DATA] as NTRO;

            // Output is WorldNode_t we need to iterate m_sceneObjects inside it.

            var sceneObjectLayerIndices = (NTROArray)data.Output["m_sceneObjectLayerIndices"];
            var sceneObjects = (NTROArray)data.Output["m_sceneObjects"];
            var i = 0;
            foreach (var entry in sceneObjects)
            {
                var layerIndice = ((NTROValue<byte>)sceneObjectLayerIndices[i]).Value;
                i++;

                // TODO: We want UI for this
                if (layerIndice == 2 || layerIndice == 4)
                {
                    continue;
                }

                // sceneObject is SceneObject_t
                var sceneObject = ((NTROValue<NTROStruct>)entry).Value;
                var renderableModel = ((NTROValue<ResourceExtRefList.ResourceReferenceInfo>)sceneObject["m_renderableModel"]).Value;
                var transform = (NTROArray)sceneObject["m_vTransform"];

                var matrix = default(Matrix4);

                // what is this
                for (var x = 0; x < 4; x++)
                {
                    var a = ((NTROValue<Vector4>)transform[x]).Value;

                    switch (x)
                    {
                        case 0: matrix.Column0 = new OpenTK.Vector4(a.X, a.Y, a.Z, a.W); break;
                        case 1: matrix.Column1 = new OpenTK.Vector4(a.X, a.Y, a.Z, a.W); break;
                        case 2: matrix.Column2 = new OpenTK.Vector4(a.X, a.Y, a.Z, a.W); break;
                        case 3: matrix.Column3 = new OpenTK.Vector4(a.X, a.Y, a.Z, a.W); break;
                    }
                }

                var tintColorWrongVector = ((NTROValue<Vector4>)sceneObject["m_vTintColor"]).Value;

                OpenTK.Vector4 tintColor;
                if (tintColorWrongVector.W == 0)
                {
                    tintColor = OpenTK.Vector4.One;
                    Console.WriteLine("Ignoring tintColor, it will f**k things up.");
                }
                else
                {
                    tintColor = new OpenTK.Vector4(tintColorWrongVector.X, tintColorWrongVector.Y, tintColorWrongVector.Z, tintColorWrongVector.W);
                }

                if (renderableModel != null)
                {
                    var newResource = FileExtensions.LoadFileByAnyMeansNecessary(renderableModel.Name + "_c", path, package);
                    if (newResource == null)
                    {
                        Console.WriteLine("unable to load model " + renderableModel.Name + "_c");

                        continue;
                    }

                    var modelEntry = new Model(newResource);
                    modelEntry.LoadMeshes(renderer, path, matrix, tintColor, package);
                }

                var renderable = ((NTROValue<ResourceExtRefList.ResourceReferenceInfo>)sceneObject["m_renderable"]).Value;

                if (renderable != null)
                {
                    var newResource = FileExtensions.LoadFileByAnyMeansNecessary(renderable.Name + "_c", path, package);
                    if (newResource == null)
                    {
                        Console.WriteLine("unable to load renderable " + renderable.Name + "_c");

                        continue;
                    }

                    renderer.AddMeshObject(new MeshObject
                    {
                        Resource = newResource,
                        Transform = matrix,
                        TintColor = tintColor
                    });
                }
            }
        }
Example #3
0
        private static void LoadEntities(NTROValue lump, Renderer.Renderer renderer, string path, Package package)
        {
            var reference = ((NTROValue <ResourceExtRefList.ResourceReferenceInfo>)lump).Value;

            if (reference == null)
            {
                return;
            }

            var newResource = FileExtensions.LoadFileByAnyMeansNecessary(reference.Name + "_c", path, package);

            if (newResource == null)
            {
                Console.WriteLine("unable to load entity lump " + reference.Name + "_c");

                return;
            }

            var entityLump = newResource.Blocks[BlockType.DATA] as EntityLump;

            var childLumps = (NTROArray)entityLump.Output["m_childLumps"];

            foreach (var lump2 in childLumps)
            {
                var lol = ((NTROValue <ResourceExtRefList.ResourceReferenceInfo>)lump).Value;

                // TODO: Should be controlled in UI with world layers
                if (lol.Name.Contains("_destruction"))
                {
                    continue;
                }

                LoadEntities(lump2, renderer, path, package);
            }

            foreach (var entity in entityLump.Datas)
            {
                var scale     = string.Empty;
                var position  = string.Empty;
                var angles    = string.Empty;
                var model     = string.Empty;
                var skin      = string.Empty;
                var colour    = new byte[0];
                var classname = string.Empty;
                var name      = string.Empty;

                foreach (var property in entity)
                {
                    //metadata
                    switch (property.Item2)
                    {
                    case 3368008710:     //World Model
                        model = property.Item3 as string;
                        break;

                    case 3827302934:     //Position
                        position = property.Item3 as string;
                        break;

                    case 3130579663:     //Angles
                        angles = property.Item3 as string;
                        break;

                    case 432137260:     //Scale
                        scale = property.Item3 as string;
                        break;

                    case 2020856412:     //Skin
                        skin = property.Item3 as string;
                        break;

                    case 588463423:     //Colour
                        colour = property.Item3 as byte[];
                        break;

                    case 3323665506:     //Classname
                        classname = property.Item3 as string;
                        break;

                    case 1094168427:
                        name = property.Item3 as string;
                        break;
                    }
                }

                if (scale == string.Empty || position == string.Empty || angles == string.Empty)
                {
                    continue;
                }

                var isCamera =
                    classname == "info_player_start" ||
                    classname == "worldspawn" ||
                    classname == "sky_camera" ||
                    classname == "point_devshot_camera" ||
                    classname == "point_camera";

                if (!isCamera && model == string.Empty)
                {
                    continue;
                }

                var scaleMatrix = Matrix4.CreateScale(ParseCoordinates(scale));

                var positionVector = ParseCoordinates(position);
                var positionMatrix = Matrix4.CreateTranslation(positionVector);

                var pitchYawRoll = ParseCoordinates(angles);
                var rollMatrix   = Matrix4.CreateRotationX(MathHelper.DegreesToRadians(pitchYawRoll.Z)); // Roll
                var pitchMatrix  = Matrix4.CreateRotationY(MathHelper.DegreesToRadians(pitchYawRoll.X)); // Pitch
                var yawMatrix    = Matrix4.CreateRotationZ(MathHelper.DegreesToRadians(pitchYawRoll.Y)); // Yaw

                var rotationMatrix       = rollMatrix * pitchMatrix * yawMatrix;
                var transformationMatrix = scaleMatrix * rotationMatrix * positionMatrix;

                if (isCamera)
                {
                    if (classname == "worldspawn")
                    {
                        renderer.SetDefaultWorldCamera(positionVector);
                    }
                    else
                    {
                        renderer.AddCamera(name == string.Empty ? $"{classname} #{anonymousCameraCount++}" : name, transformationMatrix);
                    }

                    continue;
                }

                var objColor = Vector4.One;

                // Parse colour if present
                if (colour.Length == 4)
                {
                    for (var i = 0; i < 4; i++)
                    {
                        objColor[i] = colour[i] / 255.0f;
                    }
                }

                var newEntity = FileExtensions.LoadFileByAnyMeansNecessary(model + "_c", path, package);
                if (newEntity == null)
                {
                    Console.WriteLine($"unable to load entity {model}_c");

                    continue;
                }

                var entityModel = new Model(newEntity);
                entityModel.LoadMeshes(renderer, path, transformationMatrix, objColor, package, skin);
            }
        }
        private static void LoadEntities(NTROValue lump, Renderer.Renderer renderer, string path, Package package)
        {
            var reference = ((NTROValue<ResourceExtRefList.ResourceReferenceInfo>)lump).Value;
            if (reference == null)
            {
                return;
            }

            var newResource = FileExtensions.LoadFileByAnyMeansNecessary(reference.Name + "_c", path, package);
            if (newResource == null)
            {
                Console.WriteLine("unable to load entity lump " + reference.Name + "_c");

                return;
            }

            var entityLump = newResource.Blocks[BlockType.DATA] as EntityLump;

            var childLumps = (NTROArray)entityLump.Output["m_childLumps"];

            foreach (var lump2 in childLumps)
            {
                var lol = ((NTROValue<ResourceExtRefList.ResourceReferenceInfo>)lump).Value;

                // TODO: Should be controlled in UI with world layers
                if (lol.Name.Contains("_destruction"))
                {
                    continue;
                }

                LoadEntities(lump2, renderer, path, package);
            }

            foreach (var entity in entityLump.Datas)
            {
                var scale = string.Empty;
                var position = string.Empty;
                var angles = string.Empty;
                var model = string.Empty;
                var skin = string.Empty;
                var colour = new byte[0];
                var classname = string.Empty;
                var name = string.Empty;

                foreach (var property in entity)
                {
                    //metadata
                    switch (property.Item2)
                    {
                        case 3368008710: //World Model
                            model = property.Item3 as string;
                            break;
                        case 3827302934: //Position
                            position = property.Item3 as string;
                            break;
                        case 3130579663: //Angles
                            angles = property.Item3 as string;
                            break;
                        case 432137260: //Scale
                            scale = property.Item3 as string;
                            break;
                        case 2020856412: //Skin
                            skin = property.Item3 as string;
                            break;
                        case 588463423: //Colour
                            colour = property.Item3 as byte[];
                            break;
                        case 3323665506: //Classname
                            classname = property.Item3 as string;
                            break;
                        case 1094168427:
                            name = property.Item3 as string;
                            break;
                    }
                }

                if (scale == string.Empty || position == string.Empty || angles == string.Empty)
                {
                    continue;
                }

                if (classname == "point_camera" || classname == "vr_teleport_marker" || model != string.Empty)
                {
                    var scaleMatrix = Matrix4.CreateScale(ParseCoordinates(scale));
                    var positionMatrix = Matrix4.CreateTranslation(ParseCoordinates(position));

                    var rotationVector = ParseCoordinates(angles);
                    var rotationMatrix = Matrix4.CreateRotationX(MathHelper.DegreesToRadians(rotationVector.Z));
                    rotationMatrix *= Matrix4.CreateRotationY(MathHelper.DegreesToRadians(rotationVector.X));
                    rotationMatrix *= Matrix4.CreateRotationZ(MathHelper.DegreesToRadians(rotationVector.Y));

                    var megaMatrix = scaleMatrix * rotationMatrix * positionMatrix;

                    var objColor = Vector4.One;
                    // Parse colour if present
                    if (colour.Length == 4)
                    {
                        for (var i = 0; i < 4; i++)
                        {
                            objColor[i] = colour[i] / 255.0f;
                        }
                    }

                    //This model is hardcoded into the FGD
                    if (classname == "vr_teleport_marker")
                    {
                        model = "models/effects/teleport/teleport_marker.vmdl";
                    }

                    if (classname == "point_camera")
                    {
                        renderer.AddCamera(name == string.Empty ? $"Camera {anonymousCameraCount++}" : name, megaMatrix);
                    }
                    else
                    {
                        var newEntity = FileExtensions.LoadFileByAnyMeansNecessary(model + "_c", path, package);
                        if (newEntity == null)
                        {
                            Console.WriteLine("unable to load entity " + model + "_c");

                            continue;
                        }

                        var entityModel = new Model(newEntity);
                        entityModel.LoadMeshes(renderer, path, megaMatrix, objColor, package, skin);
                    }
                }
            }
        }
Example #5
0
        internal void AddMeshes(Renderer.Renderer renderer, string path, Package package)
        {
            var data = Resource.Blocks[BlockType.DATA] as NTRO;

            var sceneObjectLayerIndices = (NTROArray)data.Output["m_sceneObjectLayerIndices"];
            var sceneObjects            = (NTROArray)data.Output["m_sceneObjects"];
            var i = 0;

            // Output is WorldNode_t we need to iterate m_sceneObjects inside it
            foreach (var entry in sceneObjects)
            {
                var layerIndice = ((NTROValue <byte>)sceneObjectLayerIndices[i]).Value;
                i++;

                // TODO: We want UI for this
                if (layerIndice == 2 || layerIndice == 4)
                {
                    continue;
                }

                // sceneObject is SceneObject_t
                var sceneObject     = ((NTROValue <NTROStruct>)entry).Value;
                var renderableModel = ((NTROValue <ResourceExtRefList.ResourceReferenceInfo>)sceneObject["m_renderableModel"]).Value;
                var transform       = (NTROArray)sceneObject["m_vTransform"];

                var matrix = default(Matrix4);

                // what is this
                for (var x = 0; x < 4; x++)
                {
                    var a = ((NTROValue <System.Numerics.Vector4>)transform[x]).Value;

                    switch (x)
                    {
                    case 0: matrix.Column0 = new Vector4(a.X, a.Y, a.Z, a.W); break;

                    case 1: matrix.Column1 = new Vector4(a.X, a.Y, a.Z, a.W); break;

                    case 2: matrix.Column2 = new Vector4(a.X, a.Y, a.Z, a.W); break;

                    case 3: matrix.Column3 = new Vector4(a.X, a.Y, a.Z, a.W); break;
                    }
                }

                var tintColorWrongVector = ((NTROValue <System.Numerics.Vector4>)sceneObject["m_vTintColor"]).Value;

                Vector4 tintColor;
                if (tintColorWrongVector.W == 0)
                {
                    tintColor = Vector4.One;
                    Console.WriteLine("Ignoring tintColor, it will f**k things up.");
                }
                else
                {
                    tintColor = new Vector4(tintColorWrongVector.X, tintColorWrongVector.Y, tintColorWrongVector.Z, tintColorWrongVector.W);
                }

                if (renderableModel != null)
                {
                    var newResource = FileExtensions.LoadFileByAnyMeansNecessary(renderableModel.Name + "_c", path, package);
                    if (newResource == null)
                    {
                        Console.WriteLine("unable to load model " + renderableModel.Name + "_c");

                        continue;
                    }

                    var modelEntry = new Model(newResource);
                    modelEntry.LoadMeshes(renderer, path, matrix, tintColor, package);
                }

                var renderable = ((NTROValue <ResourceExtRefList.ResourceReferenceInfo>)sceneObject["m_renderable"]).Value;

                if (renderable != null)
                {
                    var newResource = FileExtensions.LoadFileByAnyMeansNecessary(renderable.Name + "_c", path, package);
                    if (newResource == null)
                    {
                        Console.WriteLine("unable to load renderable " + renderable.Name + "_c");

                        continue;
                    }

                    renderer.AddMeshObject(new MeshObject
                    {
                        Resource  = newResource,
                        Transform = matrix,
                        TintColor = tintColor,
                    });
                }
            }
        }
Example #6
0
        private static void LoadEntities(NTROValue lump, Renderer.Renderer renderer, string path, Package package)
        {
            var reference = ((NTROValue <ResourceExtRefList.ResourceReferenceInfo>)lump).Value;

            if (reference == null)
            {
                return;
            }

            var newResource = FileExtensions.LoadFileByAnyMeansNecessary(reference.Name + "_c", path, package);

            if (newResource == null)
            {
                Console.WriteLine("unable to load entity lump " + reference.Name + "_c");

                return;
            }

            var entityLump = newResource.Blocks[BlockType.DATA] as EntityLump;

            var childLumps = (NTROArray)entityLump.Output["m_childLumps"];

            foreach (var lump2 in childLumps)
            {
                var lol = ((NTROValue <ResourceExtRefList.ResourceReferenceInfo>)lump).Value;

                // TODO: Should be controlled in UI with world layers
                if (lol.Name.Contains("_destruction"))
                {
                    continue;
                }

                LoadEntities(lump2, renderer, path, package);
            }

            foreach (var entity in entityLump.Datas)
            {
                var scale     = string.Empty;
                var position  = string.Empty;
                var angles    = string.Empty;
                var model     = string.Empty;
                var skin      = string.Empty;
                var colour    = new byte[0];
                var classname = string.Empty;
                var name      = string.Empty;

                foreach (var property in entity)
                {
                    //metadata
                    switch (property.Item2)
                    {
                    case 3368008710:     //World Model
                        model = property.Item3 as string;
                        break;

                    case 3827302934:     //Position
                        position = property.Item3 as string;
                        break;

                    case 3130579663:     //Angles
                        angles = property.Item3 as string;
                        break;

                    case 432137260:     //Scale
                        scale = property.Item3 as string;
                        break;

                    case 2020856412:     //Skin
                        skin = property.Item3 as string;
                        break;

                    case 588463423:     //Colour
                        colour = property.Item3 as byte[];
                        break;

                    case 3323665506:     //Classname
                        classname = property.Item3 as string;
                        break;

                    case 1094168427:
                        name = property.Item3 as string;
                        break;
                    }
                }

                if (scale == string.Empty || position == string.Empty || angles == string.Empty)
                {
                    continue;
                }

                if (classname == "point_camera" || classname == "vr_teleport_marker" || model != string.Empty)
                {
                    var scaleMatrix    = Matrix4.CreateScale(ParseCoordinates(scale));
                    var positionMatrix = Matrix4.CreateTranslation(ParseCoordinates(position));

                    var rotationVector = ParseCoordinates(angles);
                    var rotationMatrix = Matrix4.CreateRotationX(MathHelper.DegreesToRadians(rotationVector.Z));
                    rotationMatrix *= Matrix4.CreateRotationY(MathHelper.DegreesToRadians(rotationVector.X));
                    rotationMatrix *= Matrix4.CreateRotationZ(MathHelper.DegreesToRadians(rotationVector.Y));

                    var megaMatrix = scaleMatrix * rotationMatrix * positionMatrix;

                    var objColor = Vector4.One;
                    // Parse colour if present
                    if (colour.Length == 4)
                    {
                        for (var i = 0; i < 4; i++)
                        {
                            objColor[i] = colour[i] / 255.0f;
                        }
                    }

                    //This model is hardcoded into the FGD
                    if (classname == "vr_teleport_marker")
                    {
                        model = "models/effects/teleport/teleport_marker.vmdl";
                    }

                    if (classname == "point_camera")
                    {
                        renderer.AddCamera(name == string.Empty ? $"Camera {anonymousCameraCount++}" : name, megaMatrix);
                    }
                    else
                    {
                        var newEntity = FileExtensions.LoadFileByAnyMeansNecessary(model + "_c", path, package);
                        if (newEntity == null)
                        {
                            Console.WriteLine("unable to load entity " + model + "_c");

                            continue;
                        }

                        var entityModel = new Model(newEntity);
                        entityModel.LoadMeshes(renderer, path, megaMatrix, objColor, package, skin);
                    }
                }
            }
        }