Пример #1
0
        /// <summary>
        /// Set the properties, then call create
        /// NOTE:  This adds itself to the viewport and world.  In the future, that should be handled by the caller
        /// </summary>
        public void CreateAsteroid(MaterialManager materialManager, Map map, SharedVisuals sharedVisuals, Vector3D position)
        {
            _map = map;

            #region WPF Model

            // Material
            MaterialGroup materials = new MaterialGroup();
            materials.Children.Add(new DiffuseMaterial(Brushes.Gray));
            materials.Children.Add(new SpecularMaterial(Brushes.Silver, 100d));

            // Geometry Model
            GeometryModel3D geometry = new GeometryModel3D();
            geometry.Material     = materials;
            geometry.BackMaterial = materials;
            geometry.Geometry     = sharedVisuals.AsteroidMesh;
            geometry.Transform    = new ScaleTransform3D(_radius, _radius, _radius);

            // Model Visual
            ModelVisual3D model = new ModelVisual3D();
            model.Content   = geometry;
            model.Transform = new TranslateTransform3D(position);

            // Add to the viewport
            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #region Physics Body

            // Make a physics body that represents this shape
            _physicsBody = new ConvexBody3D(_map.World, model);
            //_physicsBody = new ConvexBody3D(_map.World, model, ConvexBody3D.CollisionShape.Sphere, _radius, _radius, _radius);   // for some reason, this is throwing an exception.  debug it

            _physicsBody.MaterialGroupID = materialManager.AsteroidMaterialID;

            _physicsBody.NewtonBody.UserData = this;

            _physicsBody.Mass = Convert.ToSingle(_mass);

            _physicsBody.LinearDamping  = .01f;
            _physicsBody.AngularDamping = new Vector3D(.01f, .01f, .01f);
            _physicsBody.Override2DEnforcement_Rotation = true;

            _physicsBody.ApplyForce += new BodyForceEventHandler(Body_ApplyForce);

            #endregion

            // Add to the map
            _map.AddItem(this);
        }
Пример #2
0
        public void CreateMineral(MaterialManager materialManager, Map map, SharedVisuals sharedVisuals, Vector3D position, bool randomOrientation, double volumeInCubicMeters)
        {
            _map = map;
            _sharedVisuals = sharedVisuals;

            if (_mineralType == MineralType.Custom)
            {
                #region Validate

                if (_numSides < 3)
                {
                    throw new ApplicationException("The number of sides must at least be 3");
                }

                if (_rings.Count == 0)
                {
                    throw new ApplicationException("Need at least one ring");
                }

                #endregion
            }
            else
            {
                // Overwrite my public properties based on the mineral type
                StoreSettingsForMineralType(volumeInCubicMeters);
            }

            RotateTransform3D randomRotation = null;
            if (randomOrientation)
            {
                randomRotation = new RotateTransform3D(new AxisAngleRotation3D(Math3D.GetRandomVector_Spherical(1d), Math1D.GetNearZeroValue(360d)));
            }

            if (_mineralType == MineralType.Rixium)
            {
                #region Rixium Visuals

                Model3DGroup ringModels = new Model3DGroup();

                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, -.6), .38, .5, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, -.3), .44, .75, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, 0), .5, 1, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, .3), .44, .75, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, .6), .38, .5, randomRotation));

                //TODO:  Look at the global lighting options
                PointLight pointLight = new PointLight();
                pointLight.Color = Color.FromArgb(255, 54, 147, 168);
                pointLight.Range = 20;
                pointLight.LinearAttenuation = .33;
                ringModels.Children.Add(pointLight);

                ModelVisual3D ringModel = new ModelVisual3D();        // this is the expensive one, so as few of these should be made as possible
                ringModel.Content = ringModels;

                _visuals.Add(ringModel);
                _map.Viewport.Children.Add(ringModel);

                #endregion
            }

            #region WPF Model

            // Material
            MaterialGroup materials = new MaterialGroup();
            if (_diffuseColor.A > 0)
            {
                materials.Children.Add(new DiffuseMaterial(new SolidColorBrush(_diffuseColor)));
            }

            if (_specularColor.A > 0)
            {
                materials.Children.Add(new SpecularMaterial(new SolidColorBrush(_specularColor), _specularPower));
            }

            if (_emissiveColor.A > 0)
            {
                materials.Children.Add(new EmissiveMaterial(new SolidColorBrush(_emissiveColor)));
            }

            // Geometry Model
            GeometryModel3D geometry = new GeometryModel3D();
            geometry.Material = materials;
            geometry.BackMaterial = materials;

            if (_mineralType == MineralType.Custom)
            {
                geometry.Geometry = UtilityWPF.GetMultiRingedTube_ORIG(_numSides, _rings, false, true);
            }
            else
            {
                geometry.Geometry = _sharedVisuals.GetMineralMesh(_mineralType);
            }
            if (randomOrientation)
            {
                geometry.Transform = randomRotation;
            }

            // Model Visual
            ModelVisual3D model = new ModelVisual3D();
            model.Content = geometry;
            model.Transform = new TranslateTransform3D(position);

            // Add to the viewport
            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #region Physics Body

            // Make a physics body that represents this shape
            _physicsBody = new ConvexBody3D(_map.World, model);

            _physicsBody.MaterialGroupID = materialManager.MineralMaterialID;

            _physicsBody.NewtonBody.UserData = this;

            _physicsBody.Mass = Convert.ToSingle(_mass);

            _physicsBody.LinearDamping = .01f;
            _physicsBody.AngularDamping = new Vector3D(.01f, .01f, .01f);
            _physicsBody.Override2DEnforcement_Rotation = true;

            _physicsBody.ApplyForce += new BodyForceEventHandler(Body_ApplyForce);

            #endregion

            // Add to the map
            _map.AddItem(this);
        }
Пример #3
0
        public void CreateMineral(MaterialManager materialManager, Map map, SharedVisuals sharedVisuals, Vector3D position, bool randomOrientation, double volumeInCubicMeters)
        {
            _map           = map;
            _sharedVisuals = sharedVisuals;

            if (_mineralType == MineralType.Custom)
            {
                #region Validate

                if (_numSides < 3)
                {
                    throw new ApplicationException("The number of sides must at least be 3");
                }

                if (_rings.Count == 0)
                {
                    throw new ApplicationException("Need at least one ring");
                }

                #endregion
            }
            else
            {
                // Overwrite my public properties based on the mineral type
                StoreSettingsForMineralType(volumeInCubicMeters);
            }

            RotateTransform3D randomRotation = null;
            if (randomOrientation)
            {
                randomRotation = new RotateTransform3D(new AxisAngleRotation3D(Math3D.GetRandomVector_Spherical(1d), Math1D.GetNearZeroValue(360d)));
            }

            if (_mineralType == MineralType.Rixium)
            {
                #region Rixium Visuals

                Model3DGroup ringModels = new Model3DGroup();

                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, -.6), .38, .5, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, -.3), .44, .75, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, 0), .5, 1, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, .3), .44, .75, randomRotation));
                ringModels.Children.Add(GetRixiumTorusVisual(new Vector3D(0, 0, .6), .38, .5, randomRotation));

                //TODO:  Look at the global lighting options
                PointLight pointLight = new PointLight();
                pointLight.Color             = Color.FromArgb(255, 54, 147, 168);
                pointLight.Range             = 20;
                pointLight.LinearAttenuation = .33;
                ringModels.Children.Add(pointLight);

                ModelVisual3D ringModel = new ModelVisual3D();        // this is the expensive one, so as few of these should be made as possible
                ringModel.Content = ringModels;

                _visuals.Add(ringModel);
                _map.Viewport.Children.Add(ringModel);

                #endregion
            }

            #region WPF Model

            // Material
            MaterialGroup materials = new MaterialGroup();
            if (_diffuseColor.A > 0)
            {
                materials.Children.Add(new DiffuseMaterial(new SolidColorBrush(_diffuseColor)));
            }

            if (_specularColor.A > 0)
            {
                materials.Children.Add(new SpecularMaterial(new SolidColorBrush(_specularColor), _specularPower));
            }

            if (_emissiveColor.A > 0)
            {
                materials.Children.Add(new EmissiveMaterial(new SolidColorBrush(_emissiveColor)));
            }

            // Geometry Model
            GeometryModel3D geometry = new GeometryModel3D();
            geometry.Material     = materials;
            geometry.BackMaterial = materials;

            if (_mineralType == MineralType.Custom)
            {
                geometry.Geometry = UtilityWPF.GetMultiRingedTube_ORIG(_numSides, _rings, false, true);
            }
            else
            {
                geometry.Geometry = _sharedVisuals.GetMineralMesh(_mineralType);
            }
            if (randomOrientation)
            {
                geometry.Transform = randomRotation;
            }

            // Model Visual
            ModelVisual3D model = new ModelVisual3D();
            model.Content   = geometry;
            model.Transform = new TranslateTransform3D(position);

            // Add to the viewport
            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #region Physics Body

            // Make a physics body that represents this shape
            _physicsBody = new ConvexBody3D(_map.World, model);

            _physicsBody.MaterialGroupID = materialManager.MineralMaterialID;

            _physicsBody.NewtonBody.UserData = this;

            _physicsBody.Mass = Convert.ToSingle(_mass);

            _physicsBody.LinearDamping  = .01f;
            _physicsBody.AngularDamping = new Vector3D(.01f, .01f, .01f);
            _physicsBody.Override2DEnforcement_Rotation = true;

            _physicsBody.ApplyForce += new BodyForceEventHandler(Body_ApplyForce);

            #endregion

            // Add to the map
            _map.AddItem(this);
        }
Пример #4
0
        /// <summary>
        /// Set the properties, then call create
        /// NOTE:  This adds itself to the viewport and world.  In the future, that should be handled by the caller
        /// </summary>
        public void CreateShip(MaterialManager materialManager, SharedVisuals sharedVisuals, Map map, ProgressBarGame progressBarCargo, ProgressBarGame progressBarFuel)
        {
            const double THRUSTLINELENGTH = .5d;
            const double THRUSTLINELENGTH_EXTRA = .75d;
            const double THRUSTLINELENGTH_TURN = .3;

            _sharedVisuals = sharedVisuals;
            _map = map;
            _progressBarCargo = progressBarCargo;
            _progressBarFuel = progressBarFuel;

            #region Thrusters

            // These need to be definded before the visuals are created
            double radians = Math1D.DegreesToRadians(225);
            _thrusterOffset_BottomLeft = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);
            radians = Math1D.DegreesToRadians(135);
            _thrusterOffset_TopLeft = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);

            radians = Math1D.DegreesToRadians(315);
            _thrusterOffset_BottomRight = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);
            radians = Math1D.DegreesToRadians(45);
            _thrusterOffset_TopRight = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);

            _thrustForce = 100d;
            _torqueballLeftRightThrusterForce = -10d;

            #region Define ThrustLines

            //NOTE: The ThrustLine class will add/remove visuals directly from the viewport.  There's no need for the map to get involved

            // The reference to the fuel tank will be made when I create the tank

            ThrustLine thrustLine;

            // Up
            _thrustLines.Add(Key.Up, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _thrustForce, _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Up].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _thrustForce, _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Up].Add(thrustLine);

            // W
            _thrustLines.Add(Key.W, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * (_thrustForce * 2d), _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.W].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * (_thrustForce * 2d), _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.W].Add(thrustLine);

            // Down
            _thrustLines.Add(Key.Down, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _thrustForce, _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Down].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _thrustForce, _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Down].Add(thrustLine);

            // S
            _thrustLines.Add(Key.S, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * (_thrustForce * 2d), _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.S].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * (_thrustForce * 2d), _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.S].Add(thrustLine);

            // Left
            _thrustLines.Add(Key.Left, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Left].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Left].Add(thrustLine);

            // Right
            _thrustLines.Add(Key.Right, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Right].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Right].Add(thrustLine);

            // A
            _thrustLines.Add(Key.A, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(-1, 0, 0) * _thrustForce, _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.A].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(-1, 0, 0) * _thrustForce, _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.A].Add(thrustLine);

            // D
            _thrustLines.Add(Key.D, new List<ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(1, 0, 0) * _thrustForce, _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.D].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(1, 0, 0) * _thrustForce, _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.D].Add(thrustLine);

            #endregion

            #endregion

            MaterialGroup material = null;
            GeometryModel3D geometry = null;
            Model3DGroup models = new Model3DGroup();
            ModelVisual3D model = null;

            #region Interior Extra Visuals

            // These are visuals that will stay oriented to the ship, but don't count in collision calculations

            #region Thrusters

            // These are the little balls, not the thrust lines

            double thrusterLocScale = 1d;

            models.Children.Add(GetThrusterVisual(_thrusterOffset_BottomLeft * thrusterLocScale));
            models.Children.Add(GetThrusterVisual(_thrusterOffset_BottomRight * thrusterLocScale));
            models.Children.Add(GetThrusterVisual(_thrusterOffset_TopLeft * thrusterLocScale));
            models.Children.Add(GetThrusterVisual(_thrusterOffset_TopRight * thrusterLocScale));

            #endregion
            #region Cargo Bay

            //TODO:  Make a visual for this (probably pretty cube like)

            _cargoBay = new CargoBay(_cargoBayMass, _cargoBayVolume);

            _progressBarCargo.Minimum = 0d;
            _progressBarCargo.Maximum = _cargoBay.MaxVolume;
            _progressBarCargo.Value = 0d;

            #endregion
            #region Fuel Tank

            //TODO:  This visual should be a pill

            _fuelTank = new FuelTank();
            _fuelTank.DryMass = _fuelTankMass;
            _fuelTank.QuantityMax = _fuelTankCapacity;
            _fuelTank.QuantityCurrent = _fuelTank.QuantityMax;		// a full tank with the purchace of a new ship!!!
            _fuelTank.FuelDensity = _fuelDensity;

            _progressBarFuel.Minimum = 0d;
            _progressBarFuel.Maximum = _fuelTank.QuantityMax;
            _progressBarFuel.Value = _fuelTank.QuantityCurrent;

            // Link to the thrusters
            foreach (List<ThrustLine> thrustLines in _thrustLines.Values)
            {
                foreach (ThrustLine thrustLine1 in thrustLines)
                {
                    thrustLine1.FuelToThrustRatio = _fuelThrustRatio;
                    thrustLine1.FuelTank = _fuelTank;
                }
            }

            #endregion

            #region Core

            // This just looks stupid.  The idea is that you would see the various components (which would also be point masses).  But until
            // the user can modify their ship, it's just an arbitrary ellipse that is ugly

            //// Material
            //material = new MaterialGroup();
            //material.Children.Add(new DiffuseMaterial(Brushes.DimGray));
            //material.Children.Add(new SpecularMaterial(Brushes.DimGray, 100d));

            //// Geometry Model
            //geometry = new GeometryModel3D();
            //geometry.Material = material;
            //geometry.BackMaterial = material;
            //geometry.Geometry = UtilityWPF.GetSphere(5, .45, .25, .05);
            //geometry.Transform = new TranslateTransform3D(0, this.RadiusY * -.25, 0);

            //// Model Visual
            //model = new ModelVisual3D();
            //model.Content = geometry;

            ////NOTE: model.Transform is set to the physics body's transform every frame

            //// Add to the viewport
            //_viewport.Children.Add(model);

            //_visuals.Add(model);

            #endregion

            // Make a model visual for what I have so far
            model = new ModelVisual3D();        // this is the expensive one, so as few of these should be made as possible
            model.Content = models;

            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #region WPF Collision Model

            // Material
            //NOTE:  There seems to be an issue with drawing objects inside a semitransparent object - I think they have to be added in a certain order or something
            //Brush skinBrush = new SolidColorBrush(Color.FromArgb(50, _hullColor.R, _hullColor.G, _hullColor.B));  // making the skin semitransparent, so you can see the components inside
            Brush skinBrush = new SolidColorBrush(_hullColor);  // decided to make it opaque, since I'm not showing anything inside

            material = new MaterialGroup();
            material.Children.Add(new DiffuseMaterial(skinBrush));
            material.Children.Add(new SpecularMaterial(Brushes.White, 75d));     // more reflective (and white light)

            MaterialGroup backMaterial = new MaterialGroup();
            backMaterial.Children.Add(new DiffuseMaterial(skinBrush));
            backMaterial.Children.Add(new SpecularMaterial(new SolidColorBrush(Color.FromArgb(255, 20, 20, 20)), 10d));       // dark light, and not very reflective

            // Geometry Model
            geometry = new GeometryModel3D();
            geometry.Material = material;
            geometry.BackMaterial = backMaterial;
            geometry.Geometry = UtilityWPF.GetSphere_LatLon(5, this.RadiusX, this.RadiusY, this.RadiusZ);

            // Transform
            Transform3DGroup transform = new Transform3DGroup();		// rotate needs to be added before translate
            transform.Children.Add(new RotateTransform3D(new AxisAngleRotation3D(new Vector3D(1, 0, 0), 0)));
            transform.Children.Add(new TranslateTransform3D(new Vector3D(0, 0, 0)));

            // Model Visual
            model = new ModelVisual3D();
            model.Content = geometry;
            model.Transform = transform;

            _physicsModel = model;    // remember this, so I don't set its transform
            _visuals.Add(model);

            // Add to the viewport (the physics body constructor requires it to be added)
            _map.Viewport.Children.Add(model);

            #endregion
            #region Physics Body

            // Make a physics body that represents this shape
            _physicsBody = new ConvexBody3D(_map.World, model);

            _physicsBody.MaterialGroupID = materialManager.ShipMaterialID;

            _physicsBody.NewtonBody.UserData = this;

            _physicsBody.Mass = Convert.ToSingle(this.TotalMass);

            _physicsBody.LinearDamping = .01f;
            //_physicsBody.AngularDamping = new Vector3D(.01f, .01f, .01f);
            //_physicsBody.AngularDamping = new Vector3D(10f, 10f, 10f);
            _physicsBody.AngularDamping = new Vector3D(1f, 1f, 1f);

            _physicsBody.ApplyForce += new BodyForceEventHandler(Body_ApplyForce);

            #endregion

            #region Exterior Extra Visuals

            // There is a bug in WPF where visuals added after a semitransparent one won't show inside.  The cockpit looks stupid when you can see
            // it inside the skin

            #region Cockpit

            // Material
            material = new MaterialGroup();
            material.Children.Add(new DiffuseMaterial(new SolidColorBrush(UtilityWPF.AlphaBlend(Colors.Teal, Colors.DimGray, .2d))));
            material.Children.Add(new SpecularMaterial(Brushes.White, 100d));

            // Geometry Model
            geometry = new GeometryModel3D();
            geometry.Material = material;
            geometry.BackMaterial = material;
            //geometry.Geometry = UtilityWPF.GetSphere(3, .4, .2, .3);
            geometry.Geometry = UtilityWPF.GetSphere_LatLon(3, .45, .25, .25);
            geometry.Transform = new TranslateTransform3D(0, this.RadiusY * .5, 0);

            // Model Visual
            model = new ModelVisual3D();
            model.Content = geometry;

            // Add to the viewport
            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion
            #region Headlight

            SpotLight spotLight = new SpotLight();
            //spotLight.Color = Color.FromArgb(255, 50, 170, 50);
            spotLight.Color = UtilityWPF.AlphaBlend(Colors.White, _hullColor, .25d);
            spotLight.Direction = new Vector3D(0, 1, 0);
            spotLight.OuterConeAngle = 25;
            spotLight.InnerConeAngle = 5;
            //spotLight.LinearAttenuation = .1;
            spotLight.QuadraticAttenuation = .0001;
            spotLight.Range = 1000;

            model = new ModelVisual3D();
            model.Content = spotLight;

            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #endregion

            // Add to the map
            _map.AddItem(this);
        }
Пример #5
0
        /// <summary>
        /// Set the properties, then call create
        /// NOTE:  This adds itself to the viewport and world.  In the future, that should be handled by the caller
        /// </summary>
        public void CreateShip(MaterialManager materialManager, SharedVisuals sharedVisuals, Map map, ProgressBarGame progressBarCargo, ProgressBarGame progressBarFuel)
        {
            const double THRUSTLINELENGTH       = .5d;
            const double THRUSTLINELENGTH_EXTRA = .75d;
            const double THRUSTLINELENGTH_TURN  = .3;

            _sharedVisuals    = sharedVisuals;
            _map              = map;
            _progressBarCargo = progressBarCargo;
            _progressBarFuel  = progressBarFuel;

            #region Thrusters

            // These need to be definded before the visuals are created
            double radians = Math1D.DegreesToRadians(225);
            _thrusterOffset_BottomLeft = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);
            radians = Math1D.DegreesToRadians(135);
            _thrusterOffset_TopLeft = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);

            radians = Math1D.DegreesToRadians(315);
            _thrusterOffset_BottomRight = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);
            radians = Math1D.DegreesToRadians(45);
            _thrusterOffset_TopRight = new Vector3D(this.RadiusX * Math.Cos(radians), this.RadiusY * Math.Sin(radians), 0);

            _thrustForce = 100d;
            _torqueballLeftRightThrusterForce = -10d;

            #region Define ThrustLines

            //NOTE: The ThrustLine class will add/remove visuals directly from the viewport.  There's no need for the map to get involved

            // The reference to the fuel tank will be made when I create the tank

            ThrustLine thrustLine;

            // Up
            _thrustLines.Add(Key.Up, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _thrustForce, _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Up].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _thrustForce, _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Up].Add(thrustLine);

            // W
            _thrustLines.Add(Key.W, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * (_thrustForce * 2d), _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.W].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * (_thrustForce * 2d), _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.W].Add(thrustLine);

            // Down
            _thrustLines.Add(Key.Down, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _thrustForce, _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Down].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _thrustForce, _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.Down].Add(thrustLine);

            // S
            _thrustLines.Add(Key.S, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * (_thrustForce * 2d), _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.S].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * (_thrustForce * 2d), _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_EXTRA;
            _thrustLines[Key.S].Add(thrustLine);

            // Left
            _thrustLines.Add(Key.Left, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Left].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Left].Add(thrustLine);

            // Right
            _thrustLines.Add(Key.Right, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, 1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Right].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(0, -1, 0) * _torqueballLeftRightThrusterForce, _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH_TURN;
            _thrustLines[Key.Right].Add(thrustLine);

            // A
            _thrustLines.Add(Key.A, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(-1, 0, 0) * _thrustForce, _thrusterOffset_TopRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.A].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(-1, 0, 0) * _thrustForce, _thrusterOffset_BottomRight);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.A].Add(thrustLine);

            // D
            _thrustLines.Add(Key.D, new List <ThrustLine>());

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(1, 0, 0) * _thrustForce, _thrusterOffset_TopLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.D].Add(thrustLine);

            thrustLine = new ThrustLine(_map.Viewport, _sharedVisuals, new Vector3D(1, 0, 0) * _thrustForce, _thrusterOffset_BottomLeft);
            thrustLine.LineMaxLength = THRUSTLINELENGTH;
            _thrustLines[Key.D].Add(thrustLine);

            #endregion

            #endregion

            MaterialGroup   material = null;
            GeometryModel3D geometry = null;
            Model3DGroup    models   = new Model3DGroup();
            ModelVisual3D   model    = null;

            #region Interior Extra Visuals

            // These are visuals that will stay oriented to the ship, but don't count in collision calculations

            #region Thrusters

            // These are the little balls, not the thrust lines

            double thrusterLocScale = 1d;

            models.Children.Add(GetThrusterVisual(_thrusterOffset_BottomLeft * thrusterLocScale));
            models.Children.Add(GetThrusterVisual(_thrusterOffset_BottomRight * thrusterLocScale));
            models.Children.Add(GetThrusterVisual(_thrusterOffset_TopLeft * thrusterLocScale));
            models.Children.Add(GetThrusterVisual(_thrusterOffset_TopRight * thrusterLocScale));

            #endregion
            #region Cargo Bay

            //TODO:  Make a visual for this (probably pretty cube like)

            _cargoBay = new CargoBay(_cargoBayMass, _cargoBayVolume);

            _progressBarCargo.Minimum = 0d;
            _progressBarCargo.Maximum = _cargoBay.MaxVolume;
            _progressBarCargo.Value   = 0d;

            #endregion
            #region Fuel Tank

            //TODO:  This visual should be a pill

            _fuelTank                 = new FuelTank();
            _fuelTank.DryMass         = _fuelTankMass;
            _fuelTank.QuantityMax     = _fuelTankCapacity;
            _fuelTank.QuantityCurrent = _fuelTank.QuantityMax;          // a full tank with the purchace of a new ship!!!
            _fuelTank.FuelDensity     = _fuelDensity;

            _progressBarFuel.Minimum = 0d;
            _progressBarFuel.Maximum = _fuelTank.QuantityMax;
            _progressBarFuel.Value   = _fuelTank.QuantityCurrent;

            // Link to the thrusters
            foreach (List <ThrustLine> thrustLines in _thrustLines.Values)
            {
                foreach (ThrustLine thrustLine1 in thrustLines)
                {
                    thrustLine1.FuelToThrustRatio = _fuelThrustRatio;
                    thrustLine1.FuelTank          = _fuelTank;
                }
            }

            #endregion

            #region Core

            // This just looks stupid.  The idea is that you would see the various components (which would also be point masses).  But until
            // the user can modify their ship, it's just an arbitrary ellipse that is ugly

            //// Material
            //material = new MaterialGroup();
            //material.Children.Add(new DiffuseMaterial(Brushes.DimGray));
            //material.Children.Add(new SpecularMaterial(Brushes.DimGray, 100d));

            //// Geometry Model
            //geometry = new GeometryModel3D();
            //geometry.Material = material;
            //geometry.BackMaterial = material;
            //geometry.Geometry = UtilityWPF.GetSphere(5, .45, .25, .05);
            //geometry.Transform = new TranslateTransform3D(0, this.RadiusY * -.25, 0);

            //// Model Visual
            //model = new ModelVisual3D();
            //model.Content = geometry;

            ////NOTE: model.Transform is set to the physics body's transform every frame

            //// Add to the viewport
            //_viewport.Children.Add(model);

            //_visuals.Add(model);

            #endregion

            // Make a model visual for what I have so far
            model         = new ModelVisual3D(); // this is the expensive one, so as few of these should be made as possible
            model.Content = models;

            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #region WPF Collision Model

            // Material
            //NOTE:  There seems to be an issue with drawing objects inside a semitransparent object - I think they have to be added in a certain order or something
            //Brush skinBrush = new SolidColorBrush(Color.FromArgb(50, _hullColor.R, _hullColor.G, _hullColor.B));  // making the skin semitransparent, so you can see the components inside
            Brush skinBrush = new SolidColorBrush(_hullColor);  // decided to make it opaque, since I'm not showing anything inside

            material = new MaterialGroup();
            material.Children.Add(new DiffuseMaterial(skinBrush));
            material.Children.Add(new SpecularMaterial(Brushes.White, 75d));     // more reflective (and white light)

            MaterialGroup backMaterial = new MaterialGroup();
            backMaterial.Children.Add(new DiffuseMaterial(skinBrush));
            backMaterial.Children.Add(new SpecularMaterial(new SolidColorBrush(Color.FromArgb(255, 20, 20, 20)), 10d));       // dark light, and not very reflective

            // Geometry Model
            geometry              = new GeometryModel3D();
            geometry.Material     = material;
            geometry.BackMaterial = backMaterial;
            geometry.Geometry     = UtilityWPF.GetSphere_LatLon(5, this.RadiusX, this.RadiusY, this.RadiusZ);

            // Transform
            Transform3DGroup transform = new Transform3DGroup();                // rotate needs to be added before translate
            transform.Children.Add(new RotateTransform3D(new AxisAngleRotation3D(new Vector3D(1, 0, 0), 0)));
            transform.Children.Add(new TranslateTransform3D(new Vector3D(0, 0, 0)));

            // Model Visual
            model           = new ModelVisual3D();
            model.Content   = geometry;
            model.Transform = transform;

            _physicsModel = model;    // remember this, so I don't set its transform
            _visuals.Add(model);

            // Add to the viewport (the physics body constructor requires it to be added)
            _map.Viewport.Children.Add(model);

            #endregion
            #region Physics Body

            // Make a physics body that represents this shape
            _physicsBody = new ConvexBody3D(_map.World, model);

            _physicsBody.MaterialGroupID = materialManager.ShipMaterialID;

            _physicsBody.NewtonBody.UserData = this;

            _physicsBody.Mass = Convert.ToSingle(this.TotalMass);

            _physicsBody.LinearDamping = .01f;
            //_physicsBody.AngularDamping = new Vector3D(.01f, .01f, .01f);
            //_physicsBody.AngularDamping = new Vector3D(10f, 10f, 10f);
            _physicsBody.AngularDamping = new Vector3D(1f, 1f, 1f);

            _physicsBody.ApplyForce += new BodyForceEventHandler(Body_ApplyForce);

            #endregion

            #region Exterior Extra Visuals

            // There is a bug in WPF where visuals added after a semitransparent one won't show inside.  The cockpit looks stupid when you can see
            // it inside the skin

            #region Cockpit

            // Material
            material = new MaterialGroup();
            material.Children.Add(new DiffuseMaterial(new SolidColorBrush(UtilityWPF.AlphaBlend(Colors.Teal, Colors.DimGray, .2d))));
            material.Children.Add(new SpecularMaterial(Brushes.White, 100d));

            // Geometry Model
            geometry              = new GeometryModel3D();
            geometry.Material     = material;
            geometry.BackMaterial = material;
            //geometry.Geometry = UtilityWPF.GetSphere(3, .4, .2, .3);
            geometry.Geometry  = UtilityWPF.GetSphere_LatLon(3, .45, .25, .25);
            geometry.Transform = new TranslateTransform3D(0, this.RadiusY * .5, 0);

            // Model Visual
            model         = new ModelVisual3D();
            model.Content = geometry;

            // Add to the viewport
            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion
            #region Headlight

            SpotLight spotLight = new SpotLight();
            //spotLight.Color = Color.FromArgb(255, 50, 170, 50);
            spotLight.Color          = UtilityWPF.AlphaBlend(Colors.White, _hullColor, .25d);
            spotLight.Direction      = new Vector3D(0, 1, 0);
            spotLight.OuterConeAngle = 25;
            spotLight.InnerConeAngle = 5;
            //spotLight.LinearAttenuation = .1;
            spotLight.QuadraticAttenuation = .0001;
            spotLight.Range = 1000;

            model         = new ModelVisual3D();
            model.Content = spotLight;

            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #endregion

            // Add to the map
            _map.AddItem(this);
        }
Пример #6
0
        /// <summary>
        /// Set the properties, then call create
        /// NOTE:  This adds itself to the viewport and world.  In the future, that should be handled by the caller
        /// </summary>
        public void CreateAsteroid(MaterialManager materialManager, Map map, SharedVisuals sharedVisuals, Vector3D position)
        {
            _map = map;

            #region WPF Model

            // Material
            MaterialGroup materials = new MaterialGroup();
            materials.Children.Add(new DiffuseMaterial(Brushes.Gray));
            materials.Children.Add(new SpecularMaterial(Brushes.Silver, 100d));

            // Geometry Model
            GeometryModel3D geometry = new GeometryModel3D();
            geometry.Material = materials;
            geometry.BackMaterial = materials;
            geometry.Geometry = sharedVisuals.AsteroidMesh;
            geometry.Transform = new ScaleTransform3D(_radius, _radius, _radius);

            // Model Visual
            ModelVisual3D model = new ModelVisual3D();
            model.Content = geometry;
            model.Transform = new TranslateTransform3D(position);

            // Add to the viewport
            _visuals.Add(model);
            _map.Viewport.Children.Add(model);

            #endregion

            #region Physics Body

            // Make a physics body that represents this shape
            _physicsBody = new ConvexBody3D(_map.World, model);
            //_physicsBody = new ConvexBody3D(_map.World, model, ConvexBody3D.CollisionShape.Sphere, _radius, _radius, _radius);   // for some reason, this is throwing an exception.  debug it

            _physicsBody.MaterialGroupID = materialManager.AsteroidMaterialID;

            _physicsBody.NewtonBody.UserData = this;

            _physicsBody.Mass = Convert.ToSingle(_mass);

            _physicsBody.LinearDamping = .01f;
            _physicsBody.AngularDamping = new Vector3D(.01f, .01f, .01f);
            _physicsBody.Override2DEnforcement_Rotation = true;

            _physicsBody.ApplyForce += new BodyForceEventHandler(Body_ApplyForce);

            #endregion

            // Add to the map
            _map.AddItem(this);
        }