Improved map rendering, shops, light bugfix, junction boxes wont break as easily

This commit is contained in:
Regalis
2015-07-27 23:45:20 +03:00
parent 4238301ad3
commit 7155f1cef0
37 changed files with 472 additions and 300 deletions

View File

@@ -175,20 +175,13 @@ namespace Subsurface
public float Bleeding
{
get { return bleeding; }
set { bleeding = value; }
set
{
if (float.IsNaN(value) || float.IsInfinity(value)) return;
bleeding = Math.Max(value, 0.0f);
}
}
//public float Blood
//{
// get { return blood; }
// set
// {
// blood = MathHelper.Clamp(value, 0.0f, 100.0f);
// if (blood == 0.0f) Kill();
// }
//}
public Item[] SelectedItems
{
get { return selectedItems; }
@@ -716,7 +709,14 @@ namespace Subsurface
public void Draw(SpriteBatch spriteBatch)
{
AnimController.Draw(spriteBatch);
//GUI.DrawLine(spriteBatch, ConvertUnits.ToDisplayUnits(animController.limbs[0].SimPosition.X, animController.limbs[0].SimPosition.Y),
// ConvertUnits.ToDisplayUnits(animController.limbs[0].SimPosition.X, animController.limbs[0].SimPosition.Y) +
// ConvertUnits.ToDisplayUnits(animController.targetMovement.X, animController.targetMovement.Y), Color.Green);
}
public void DrawFront(SpriteBatch spriteBatch)
{
if (IsNetworkPlayer)
{
Vector2 namePos = new Vector2(Position.X, -Position.Y - 80.0f) - GUI.Font.MeasureString(Info.Name) * 0.5f;
@@ -731,13 +731,12 @@ namespace Subsurface
Vector2 pos = ConvertUnits.ToDisplayUnits(AnimController.limbs[0].SimPosition);
pos.Y = -pos.Y;
if (this == Character.controlled) return;
Vector2 healthBarPos = new Vector2(Position.X - 50, -Position.Y - 50.0f);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)healthBarPos.X-2, (int)healthBarPos.Y-2, 100+4, 15+4), Color.Black, false);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)healthBarPos.X, (int)healthBarPos.Y, (int)(100.0f*(health/maxHealth)), 15), Color.Red, true);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)healthBarPos.X - 2, (int)healthBarPos.Y - 2, 100 + 4, 15 + 4), Color.Black, false);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)healthBarPos.X, (int)healthBarPos.Y, (int)(100.0f * (health / maxHealth)), 15), Color.Red, true);
//GUI.DrawLine(spriteBatch, ConvertUnits.ToDisplayUnits(animController.limbs[0].SimPosition.X, animController.limbs[0].SimPosition.Y),

View File

@@ -1,4 +1,5 @@
using Microsoft.Xna.Framework;
using System;
using System.Collections.Generic;
using System.Xml.Linq;
@@ -13,9 +14,7 @@ namespace Subsurface
public Character Character;
public readonly string File;
public int HeadSpriteId;
public Job Job;
private List<int> pickedItems;
@@ -23,6 +22,28 @@ namespace Subsurface
private Vector2[] headSpriteRange;
private Gender gender;
public int Salary;
public int HeadSpriteId;
private Sprite headSprite;
public bool StartItemsGiven;
public List<int> PickedItemIDs
{
get { return pickedItems; }
}
public Sprite HeadSprite
{
get
{
if (headSprite == null) LoadHeadSprite();
return headSprite;
}
}
public Gender Gender
{
get { return gender; }
@@ -45,25 +66,6 @@ namespace Subsurface
}
}
public int Salary;
public bool StartItemsGiven;
public List<int> PickedItemIDs
{
get { return pickedItems; }
}
private Sprite headSprite;
public Sprite HeadSprite
{
get
{
if (headSprite == null) LoadHeadSprite();
return headSprite;
}
}
public CharacterInfo(string file, string name = "", Gender gender = Gender.None, JobPrefab jobPrefab = null)
{
this.File = file;
@@ -77,8 +79,6 @@ namespace Subsurface
XDocument doc = ToolBox.TryLoadXml(file);
if (doc == null) return;
Salary = 500;
if (ToolBox.GetAttributeBool(doc.Root, "genders", false))
{
if (gender == Gender.None)
@@ -131,6 +131,8 @@ namespace Subsurface
this.Name += ToolBox.GetRandomLine(lastNamePath);
}
}
Salary = CalculateSalary();
}
private void LoadHeadSprite()
@@ -232,6 +234,20 @@ namespace Subsurface
}
}
private int CalculateSalary()
{
if (Name == null || Job == null) return 0;
int salary = Math.Abs(Name.GetHashCode()) % 100;
foreach (Skill skill in Job.Skills)
{
salary += skill.Level * 10;
}
return salary;
}
public virtual XElement Save(XElement parentElement)
{
XElement charElement = new XElement("character");
@@ -244,18 +260,16 @@ namespace Subsurface
new XAttribute("headspriteid", HeadSpriteId),
new XAttribute("startitemsgiven", StartItemsGiven));
if (Character!=null && Character.Inventory!=null)
if (Character != null && Character.Inventory != null)
{
UpdateCharacterItems();
}
if (pickedItems.Count>0)
if (pickedItems.Count > 0)
{
charElement.Add(new XAttribute("items", string.Join(",", pickedItems)));
}
Job.Save(charElement);
parentElement.Add(charElement);

View File

@@ -320,17 +320,17 @@ namespace Subsurface
}
avgVelocity = avgVelocity / limbs.Count();
float impact = Vector2.Dot((f1.Body.LinearVelocity + avgVelocity)/2.0f, -normal);
float impact = Vector2.Dot((f1.Body.LinearVelocity + avgVelocity) / 2.0f, -normal);
Limb l = (Limb)f1.Body.UserData;
if (impact > 1.0f && l.HitSound != null && l.soundTimer<=0.0f) l.HitSound.Play(Math.Min(impact / 5.0f, 1.0f), impact*100.0f, l.body.FarseerBody);
if (impact > 1.0f && l.HitSound != null && l.soundTimer <= 0.0f) l.HitSound.Play(Math.Min(impact / 5.0f, 1.0f), impact * 100.0f, l.body.FarseerBody);
if (impact > l.impactTolerance)
{
character.Health -= (impact-l.impactTolerance*0.1f);
character.Health -= (impact - l.impactTolerance * 0.1f);
strongestImpact = Math.Max(strongestImpact, impact - l.impactTolerance);
}
}

View File

@@ -3,7 +3,8 @@
<Item
name="Oxygen Tank"
Tags="smallitem"
pickdistance="150">
pickdistance="150"
price="50">
<Sprite texture ="oxygentank.png" depth="0.05"/>
@@ -16,7 +17,8 @@
<Item
name="Diving Mask"
Tags="smallitem"
pickdistance="200">
pickdistance="200"
price="50">
<Sprite texture ="DivingMask.png" depth="0.4"/>
@@ -37,7 +39,8 @@
<Item
name="Diving Suit"
pickdistance="200">
pickdistance="200"
price="200">
<Sprite texture ="DivingSuit.png" sourcerect="82,15,46,113" depth="0.4"/>

View File

@@ -7,7 +7,8 @@
Tags="smallitem"
pickdistance="150"
linkable="true"
canbepicked="true">
canbepicked="true"
price="10">
<Sprite texture ="wire.png" depth="0.55"/>
@@ -23,7 +24,8 @@
name="And Component"
Tags="smallitem"
pickdistance="150"
linkable="true">
linkable="true"
price="10">
<Sprite texture ="and.png" depth="0.8"/>
@@ -52,7 +54,8 @@
name="Or Component"
Tags="smallitem"
pickdistance="150"
linkable="true">
linkable="true"
price="10">
<Sprite texture ="or.png" depth="0.8"/>
@@ -79,7 +82,8 @@
name="Not Component"
Tags="smallitem"
pickdistance="150"
linkable="true">
linkable="true"
price="10">
<Sprite texture ="not.png" depth="0.8"/>
@@ -105,7 +109,8 @@
name="Light Component"
Tags="smallitem"
pickdistance="150"
linkable="true">
linkable="true"
price="10">
<Sprite texture ="light.png" depth="0.8"/>
@@ -133,7 +138,8 @@
name="Oxygen Detector"
Tags="smallitem"
pickdistance="150"
linkable="true">
linkable="true"
price="10">
<Sprite texture ="light.png" depth="0.8"/>
@@ -157,7 +163,8 @@
name="RegEx Find Component"
Tags="smallitem"
pickdistance="150"
linkable="true">
linkable="true"
price="10">
<Sprite texture ="light.png" depth="0.8"/>

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

View File

@@ -1,6 +1,7 @@
<locationtypes>
<None
commonness="3">
commonness="3"
symbol="Content\Map\beaconSymbol.png">
<nameformats
f0="[name]"
f1="[name]"
@@ -10,7 +11,8 @@
<City
commonness="3"
hireablecharacters="true">
hireablecharacters="true"
symbol="Content\Map\citySymbol.png">
<nameformats
f0="The City of [name]"
f1="[name] City"
@@ -20,7 +22,8 @@
<Military
commonness="1"
hireablecharacters="true">
hireablecharacters="true"
symbol="Content\Map\militarySymbol.png">
<nameformats
f0="[name] Outpost"
f1="[name] Facility"
@@ -30,7 +33,8 @@
<Research
commonness="1"
hireablecharacters="true">
hireablecharacters="true"
symbol="Content\Map\researchSymbol.png">
<nameformats
f0="[name] Research Facility"
f1="[name] Research Center"

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

View File

@@ -298,9 +298,9 @@ namespace Subsurface
public virtual void DrawChildren(SpriteBatch spriteBatch)
{
foreach (GUIComponent child in children)
for (int i = 0; i < children.Count; i++ )
{
child.Draw(spriteBatch);
children[i].Draw(spriteBatch);
}
}

View File

@@ -280,7 +280,10 @@ namespace Subsurface
Debug.WriteLine("clicked");
selected = child;
if (OnSelected != null)
OnSelected(child.UserData);
{
if (!OnSelected(child.UserData)) selected = null;
}
}
}
else

View File

@@ -0,0 +1,53 @@
using Microsoft.Xna.Framework;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace Subsurface
{
class CargoManager
{
private List<MapEntityPrefab> purchasedItems;
public CargoManager()
{
purchasedItems = new List<MapEntityPrefab>();
}
public void AddItem(MapEntityPrefab item)
{
purchasedItems.Add(item);
}
public void CreateItems()
{
WayPoint wp = WayPoint.GetRandom(SpawnType.Cargo);
if (wp==null)
{
DebugConsole.ThrowError("The submarine must have a waypoint marked as Cargo for bought items to be placed correctly!");
return;
}
Hull cargoRoom = Hull.FindHull(wp.Position);
if (wp == null)
{
DebugConsole.ThrowError("A waypoint marked as Cargo must be placed inside a room!");
return;
}
foreach (MapEntityPrefab prefab in purchasedItems)
{
Vector2 position = new Vector2(
Rand.Range(cargoRoom.Rect.X + 20, cargoRoom.Rect.Right - 20),
Rand.Range(cargoRoom.Rect.Y - cargoRoom.Rect.Height + 20.0f, cargoRoom.Rect.Y));
new Item(prefab as ItemPrefab, wp.Position);
}
purchasedItems.Clear();
}
}
}

View File

@@ -20,7 +20,7 @@ namespace Subsurface
//Constructor = constructor;
Constructor = type.GetConstructor(new Type[] { typeof(GameModePreset) });
Constructor = type.GetConstructor(new Type[] { typeof(GameModePreset)});
IsSinglePlayer = isSinglePlayer;

View File

@@ -10,50 +10,58 @@ namespace Subsurface
{
class SinglePlayerMode : GameMode
{
private const int StartCharacterAmount = 3;
//private const int StartCharacterAmount = 3;
public readonly CrewManager crewManager;
//public readonly HireManager hireManager;
private GUIButton endShiftButton;
//private int day;
//public int Day
//{
// get { return day; }
//}
public readonly CargoManager CargoManager;
public Map map;
bool crewDead;
private bool crewDead;
private float endTimer;
private bool savedOnStart;
public SinglePlayerMode(GameModePreset preset, bool generateCrew=true)
public SinglePlayerMode(GameModePreset preset)
: base(preset)
{
crewManager = new CrewManager();
CargoManager = new CargoManager();
endShiftButton = new GUIButton(new Rectangle(Game1.GraphicsWidth - 220, 20, 200, 25), "End shift", Alignment.TopLeft, GUI.style);
endShiftButton.OnClicked = EndShift;
for (int i = 0; i < StartCharacterAmount; i++)
for (int i = 0; i < 3; i++)
{
JobPrefab jobPrefab = null;
switch (i)
{
case 0:
jobPrefab = JobPrefab.List.Find(jp => jp.Name == "Captain");
break;
case 1:
jobPrefab = JobPrefab.List.Find(jp => jp.Name == "Engineer");
break;
case 2:
jobPrefab = JobPrefab.List.Find(jp => jp.Name == "Mechanic");
break;
}
CharacterInfo characterInfo =
new CharacterInfo(Character.HumanConfigFile, "", Gender.None, JobPrefab.Random());
new CharacterInfo(Character.HumanConfigFile, "", Gender.None, jobPrefab);
crewManager.characterInfos.Add(characterInfo);
}
//day = 1;
}
public SinglePlayerMode(XElement element)
: this(GameModePreset.list.Find(gm => gm.Name == "Single Player"), false)
: this(GameModePreset.list.Find(gm => gm.Name == "Single Player"))
{
//day = ToolBox.GetAttributeInt(element,"day",1);
string mapSeed = ToolBox.GetAttributeString(element, "mapseed", "a");
GenerateMap(mapSeed);
@@ -75,16 +83,14 @@ namespace Subsurface
public override void Start(TimeSpan duration)
{
CargoManager.CreateItems();
if (!savedOnStart)
{
SaveUtil.SaveGame(Game1.GameSession.SavePath);
savedOnStart = true;
//Game1.GameSession.submarine.Load();
}
endTimer = 5.0f;
crewManager.StartShift();

View File

@@ -123,7 +123,7 @@ namespace Subsurface.Items.Components
MeltDown();
return;
}
else if (temperature==0.0f)
else if (temperature == 0.0f)
{
if (powerUpTask == null || powerUpTask.IsFinished)
{

View File

@@ -50,7 +50,7 @@ namespace Subsurface.Items.Components
pt.powerLoad += (fullLoad - pt.powerLoad) / inertia;
pt.currPowerConsumption += (-fullPower - pt.currPowerConsumption) / inertia;
pt.Item.SendSignal("", "power", fullPower / Math.Max(fullLoad, 1.0f));
if (-pt.currPowerConsumption > pt.powerLoad * 2.0f) pt.item.Condition = 0.0f;
if (-pt.currPowerConsumption > Math.Max(pt.powerLoad * 2.0f, 200.0f)) pt.item.Condition -= deltaTime*10.0f;
}
}
@@ -139,7 +139,6 @@ namespace Subsurface.Items.Components
{
connection.SendSignal(signal, sender, 0.0f);
}
}
}
}
}

View File

@@ -83,6 +83,12 @@ namespace Subsurface.Items.Components
light.Position = ConvertUnits.ToDisplayUnits(item.body.Position);
}
if (item.container!= null)
{
light.Color = Color.Transparent;
return;
}
if (powerConsumption == 0.0f)
{
voltage = 1.0f;
@@ -92,9 +98,9 @@ namespace Subsurface.Items.Components
currPowerConsumption = powerConsumption;
}
if (Rand.Range(0.0f, 1.0f)<0.05f && voltage < Rand.Range(0.0f, minVoltage))
if (Rand.Range(0.0f, 1.0f) < 0.05f && voltage < Rand.Range(0.0f, minVoltage))
{
if (voltage>0.1f) sparkSounds[Rand.Int(sparkSounds.Length)].Play(1.0f, 400.0f, item.Position);
if (voltage > 0.1f) sparkSounds[Rand.Int(sparkSounds.Length)].Play(1.0f, 400.0f, item.Position);
lightBrightness = 0.0f;
}
else
@@ -117,6 +123,13 @@ namespace Subsurface.Items.Components
}
}
public override void Remove()
{
base.Remove();
light.Remove();
}
public override void ReceiveSignal(string signal, Connection connection, Item sender, float power=0.0f)
{
base.ReceiveSignal(signal, connection, sender, power);

View File

@@ -65,6 +65,8 @@ namespace Subsurface
get { return condition; }
set
{
if (float.IsNaN(value)) return;
float prev = condition;
condition = MathHelper.Clamp(value, 0.0f, 100.0f);
if (condition==0.0f && prev>0.0f)
@@ -1063,6 +1065,8 @@ namespace Subsurface
public override void FillNetworkData(NetworkEventType type, NetOutgoingMessage message, object data)
{
message.Write(condition);
switch (type)
{
case NetworkEventType.DropItem:
@@ -1077,6 +1081,8 @@ namespace Subsurface
public override void ReadNetworkData(NetworkEventType type, NetIncomingMessage message)
{
Condition = message.ReadFloat();
switch (type)
{
case NetworkEventType.DropItem:
@@ -1096,7 +1102,7 @@ namespace Subsurface
base.Remove();
//sprite.Remove();
if (body!=null) body.Remove();
if (body != null) body.Remove();
foreach (ItemComponent ic in components)
{

View File

@@ -156,6 +156,8 @@ namespace Subsurface
focusOnSelected = ToolBox.GetAttributeBool(element, "focusonselected", false);
offsetOnSelected = ToolBox.GetAttributeFloat(element, "offsetonselected", 0.0f);
price = ToolBox.GetAttributeInt(element, "price", 0);
Triggers = new List<Rectangle>();

View File

@@ -32,15 +32,15 @@ namespace Subsurface
public readonly Dictionary<string, PropertyDescriptor> properties;
float lethalPressure;
private float lethalPressure;
float surface;
float volume;
float pressure;
private float surface;
private float volume;
private float pressure;
float oxygen;
private float oxygen;
bool update;
private bool update;
float[] waveY; //displacement from the surface of the water
float[] waveVel; //velocity of the point

View File

@@ -300,6 +300,7 @@ namespace Subsurface
for (int n = -1; n < 2; n += 2)
{
int cellIndex = FindCellIndex(new Vector2(tunnelStart.X + minWidth * 0.5f * n, tunnelStart.Y), 3);
foreach (GraphEdge ge in cells[cellIndex].edges)
{
if (ge.point1.Y > cells[cellIndex].Center.Y) ge.point1.Y = borders.Height + shaftHeight;

View File

@@ -57,5 +57,10 @@ namespace Subsurface.Lights
float scale = range / ((float)lightTexture.Width / 2.0f);
spriteBatch.Draw(lightTexture, new Vector2(Position.X, -Position.Y), null, color, 0, center, scale, SpriteEffects.None, 1);
}
public void Remove()
{
Game1.LightManager.RemoveLight(this);
}
}
}

View File

@@ -76,13 +76,11 @@ namespace Subsurface.Lights
foreach (LightSource light in lights)
{
if (light.Color.A < 0.01f || light.Range < 0.01f) continue;
if (!MathUtils.CircleIntersectsRectangle(light.Position, light.Range, viewRect)) continue;
//clear alpha to 1
ClearAlphaToOne(graphics, spriteBatch);
ClearAlphaToOne(graphics, spriteBatch);
if (!MathUtils.CircleIntersectsRectangle(light.Position, light.Range, viewRect)) continue;
//draw all shadows
//write only to the alpha channel, which sets alpha to 0
graphics.RasterizerState = RasterizerState.CullNone;

View File

@@ -29,6 +29,7 @@ namespace Subsurface
get { return mapPosition; }
}
public bool Discovered;
public LocationType Type
{

View File

@@ -19,6 +19,8 @@ namespace Subsurface
private List<string> nameFormats;
private Sprite sprite;
public bool HasHireableCharacters
{
get;
@@ -35,6 +37,11 @@ namespace Subsurface
get { return nameFormats; }
}
public Sprite Sprite
{
get { return sprite; }
}
private LocationType(XElement element)
{
name = element.Name.ToString();
@@ -49,6 +56,10 @@ namespace Subsurface
{
nameFormats.Add(nameFormat.Value.ToString());
}
string spritePath = ToolBox.GetAttributeString(element, "symbol", "Content/Map/beaconSymbol.png");
sprite = new Sprite(spritePath, null, new Microsoft.Xna.Framework.Vector2(-32, -32));
}
public static LocationType Random()

View File

@@ -22,7 +22,7 @@ namespace Subsurface
private int seed;
private int size;
private static Texture2D iceTexture;
private static Sprite iceTexture;
private static Texture2D iceCraters;
private static Texture2D iceCrack;
@@ -61,7 +61,7 @@ namespace Subsurface
connections = new List<LocationConnection>();
if (iceTexture==null) iceTexture = Game1.TextureLoader.FromFile("Content/Map/iceSurface.png");
if (iceTexture==null) iceTexture = new Sprite("Content/Map/iceSurface.png", Vector2.Zero);
if (iceCraters == null) iceCraters = Game1.TextureLoader.FromFile("Content/Map/iceCraters.png");
if (iceCrack == null) iceCrack = Game1.TextureLoader.FromFile("Content/Map/iceCrack.png");
@@ -244,14 +244,18 @@ namespace Subsurface
}
private Location highlightedLocation;
public void Draw(SpriteBatch spriteBatch, Rectangle rect)
public void Draw(SpriteBatch spriteBatch, Rectangle rect, float scale = 1.0f)
{
//GUI.DrawRectangle(spriteBatch, rect, Color.DarkBlue, true);
spriteBatch.Draw(iceTexture, rect, Color.White);
Vector2 rectCenter = new Vector2(rect.Center.X, rect.Center.Y);
Vector2 offset = -currentLocation.MapPosition;
Vector2 rectCorner = new Vector2(rect.X, rect.Y);
Vector2 scale = new Vector2((float)rect.Width/ size, (float)rect.Height/size);
iceTexture.DrawTiled(spriteBatch, new Vector2(rect.X, rect.Y), new Vector2(rect.Width, rect.Height), offset, Color.White);
//spriteBatch.Draw(iceTexture, offset, rect, null, null, 0f, null, Color.White, SpriteEffects.None, 0.0f);
//Vector2 scale = new Vector2((float)rect.Width/ size, (float)rect.Height/size);
float maxDist = 20.0f;
float closestDist = 0.0f;
@@ -259,9 +263,11 @@ namespace Subsurface
for (int i = 0; i < locations.Count;i++ )
{
Location location = locations[i];
Vector2 pos = rectCorner + location.MapPosition * scale;
Vector2 pos = rectCenter + (location.MapPosition+offset) * scale;
float dist = Vector2.Distance(PlayerInput.MousePosition, new Vector2(pos.X, pos.Y));
if (!rect.Contains(pos)) continue;
float dist = Vector2.Distance(PlayerInput.MousePosition, pos);
if (dist < maxDist && (highlightedLocation == null || dist < closestDist))
{
closestDist = dist;
@@ -272,7 +278,7 @@ namespace Subsurface
foreach (LocationConnection connection in connections)
{
Color crackColor = Color.Lerp(Color.LightGreen, Color.DarkRed, connection.Difficulty/100.0f);
Color crackColor = Color.White * Math.Max(connection.Difficulty/100.0f, 0.5f);
if (highlightedLocation != currentLocation &&
connection.Locations.Contains(highlightedLocation) && connection.Locations.Contains(currentLocation))
@@ -297,32 +303,42 @@ namespace Subsurface
foreach (Vector2[] segment in connection.CrackSegments)
{
Vector2 start = segment[0] * scale + rectCorner;
Vector2 end = segment[1] * scale + rectCorner;
Vector2 start = rectCenter + (segment[0] + offset) * scale;
Vector2 end = rectCenter + (segment[1] + offset) * scale;
if (!rect.Contains(start) || !rect.Contains(end)) continue;
float dist = Vector2.Distance(start, end);
//spriteBatch.Draw(iceCrack,
// new Rectangle((int)((start.X + end.X) / 2.0f), (int)((start.Y + end.Y) / 2.0f), (int)dist, 30),
// new Rectangle(0, 0, iceCrack.Width, 60), crackColor, MathUtils.VectorToAngle(start - end),
// new Vector2(dist / 2, 30), SpriteEffects.None, 0.01f);
GUI.DrawLine(spriteBatch,
segment[0] * scale + rectCorner,
segment[1] * scale + rectCorner, crackColor);
spriteBatch.Draw(iceCrack,
new Rectangle((int)start.X, (int)start.Y, (int)dist+2, 30),
new Rectangle(0, 0, iceCrack.Width, 60), crackColor, MathUtils.VectorToAngle(end -start),
new Vector2(0, 30), SpriteEffects.None, 0.01f);
}
}
for (int i = 0; i < locations.Count; i++)
{
Location location = locations[i];
Vector2 pos = rectCorner + location.MapPosition * scale;
Vector2 pos = rectCenter + (location.MapPosition + offset) * scale;
if (!rect.Contains(pos)) continue;
int imgIndex = i % 16;
int xCell = imgIndex % 4;
int yCell = (int)Math.Floor(imgIndex / 4.0f);
spriteBatch.Draw(iceCraters, pos,
new Rectangle(xCell * 64, yCell * 64, 64, 64),
Color.White, i,
new Vector2(32, 32), 0.5f*scale, SpriteEffects.None, 0.0f);
Color color = location.Connections.Find(c => c.Locations.Contains(currentLocation))==null ? Color.White : Color.Green;
color *= (location.Discovered) ? 0.8f : 0.4f;
if (location == currentLocation) color = Color.Orange;
location.Type.Sprite.Draw(spriteBatch, pos, color);
//int imgIndex = i % 16;
//int xCell = imgIndex % 4;
//int yCell = (int)Math.Floor(imgIndex / 4.0f);
//spriteBatch.Draw(iceCraters, pos,
// new Rectangle(xCell * 64, yCell * 64, 64, 64),
// Color.White, i,
// new Vector2(32, 32), 0.5f*scale, SpriteEffects.None, 0.0f);
}
@@ -333,14 +349,13 @@ namespace Subsurface
if (location == null) continue;
Vector2 pos = rectCorner + location.MapPosition * scale;
Vector2 pos = rectCenter + (location.MapPosition + offset) * scale;
pos.X = (int)pos.X;
pos.Y = (int)pos.Y;
if (highlightedLocation==location)
if (highlightedLocation == location)
{
spriteBatch.DrawString(GUI.Font, location.Name, pos + new Vector2(-50, -20), Color.DarkRed);
spriteBatch.DrawString(GUI.Font, location.Name, pos + new Vector2(0, 50), Color.DarkRed, 0.0f, GUI.Font.MeasureString(location.Name)/2.0f, 1.0f, SpriteEffects.None, 0.0f);
}
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos.X - 4, (int)pos.Y - 4, 5 + 8, 5 + 8), Color.DarkRed, false);
}
}

View File

@@ -29,6 +29,8 @@ namespace Subsurface
//which prefab has been selected for placing
protected static MapEntityPrefab selected;
protected int price;
public string Name
{
get { return name; }
@@ -54,6 +56,11 @@ namespace Subsurface
get { return resizeVertical; }
}
public int Price
{
get { return price; }
}
public static void Init()
{
MapEntityPrefab ep = new MapEntityPrefab();

View File

@@ -10,7 +10,7 @@ using System.Collections.ObjectModel;
namespace Subsurface
{
public enum SpawnType { None, Human, Enemy };
public enum SpawnType { None, Human, Enemy, Cargo };
class WayPoint : MapEntity
{
public static List<WayPoint> WayPointList = new List<WayPoint>();
@@ -52,6 +52,7 @@ namespace Subsurface
WayPointList.Add(this);
}
public override void Draw(SpriteBatch spriteBatch, bool editing)
{
if (!editing && !Game1.DebugDraw) return;
@@ -59,7 +60,7 @@ namespace Subsurface
Point pos = new Point((int)Position.X, (int)Position.Y);
Color clr = (isSelected) ? Color.Red : Color.LightGreen;
GUI.DrawRectangle(spriteBatch, new Rectangle(pos.X, -pos.Y, rect.Width, rect.Height), clr, true);
GUI.DrawRectangle(spriteBatch, new Rectangle(pos.X - rect.Width / 2, -pos.Y - rect.Height / 2, rect.Width, rect.Height), clr, true);
foreach (MapEntity e in linkedTo)
{
@@ -102,7 +103,7 @@ namespace Subsurface
spawnType += (int)button.UserData;
if (spawnType > SpawnType.Enemy) spawnType = SpawnType.None;
if (spawnType > SpawnType.Cargo) spawnType = SpawnType.None;
if (spawnType < SpawnType.None) spawnType = SpawnType.Enemy;
spawnTypeText.Text = spawnType.ToString();

View File

@@ -284,8 +284,12 @@ namespace Subsurface.Networking
}
NetworkEvent.events.Clear();
CheckServerMessages();
try
{
CheckServerMessages();
}
catch { }
// Update current time
updateTimer = DateTime.Now + updateInterval;

View File

@@ -56,10 +56,10 @@ namespace Subsurface.Networking
public override void Update()
{
if (PlayerInput.KeyDown(Microsoft.Xna.Framework.Input.Keys.K))
{
SendRandomData();
}
//if (PlayerInput.KeyDown(Microsoft.Xna.Framework.Input.Keys.K))
//{
// SendRandomData();
//}
if (gameStarted) inGameHUD.Update((float)Physics.step);

View File

@@ -9,7 +9,7 @@ using System.Runtime.InteropServices;
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyCopyright("Copyright © Undertow Games 2014")]
[assembly: AssemblyCopyright("Copyright © Undertow Games 2015")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
@@ -31,5 +31,5 @@ using System.Runtime.InteropServices;
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("0.0.1.0")]
[assembly: AssemblyFileVersion("0.0.1.0")]
[assembly: AssemblyVersion("0.0.1.3")]
[assembly: AssemblyFileVersion("0.0.1.3")]

View File

@@ -147,13 +147,7 @@ namespace Subsurface
public void DrawMap(GraphicsDevice graphics, SpriteBatch spriteBatch)
{
System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch();
sw.Start();
Game1.LightManager.DrawLightmap(graphics, spriteBatch, cam);
sw.Stop();
System.Diagnostics.Debug.WriteLine(sw.ElapsedMilliseconds+" - "+sw.ElapsedTicks);
//----------------------------------------------------------------------------------------
//1. draw the background, characters and the parts of the submarine that are behind them
@@ -278,6 +272,8 @@ namespace Subsurface
Submarine.DrawFront(spriteBatch);
foreach (Character c in Character.CharacterList) c.DrawFront(spriteBatch);
if (Game1.GameSession != null && Game1.GameSession.Level != null)
{
Game1.GameSession.Level.Draw(spriteBatch);

View File

@@ -9,7 +9,7 @@ namespace Subsurface
{
class LobbyScreen : Screen
{
enum PanelTab { Crew = 0, Map = 1, CurrentLocation = 2 }
enum PanelTab { Crew = 0, Map = 1, CurrentLocation = 2, Store = 3 }
GUIFrame leftPanel;
GUIFrame[] rightPanel;
@@ -21,12 +21,36 @@ namespace Subsurface
GUIListBox characterList;
GUIListBox hireList;
GUIListBox selectedItemList;
SinglePlayerMode gameMode;
GUIFrame previewFrame;
GUIButton buyButton;
Level selectedLevel;
private string SelectedItemCost()
{
return selectedItemCost.ToString();
}
private int selectedItemCost
{
get
{
int cost = 0;
foreach (GUIComponent child in selectedItemList.children)
{
MapEntityPrefab ep = child.UserData as MapEntityPrefab;
if (ep == null) continue;
cost += ep.Price;
}
return cost;
}
}
public LobbyScreen()
{
Rectangle panelRect = new Rectangle(
@@ -44,17 +68,21 @@ namespace Subsurface
"", Color.Transparent, Color.White, Alignment.Left, GUI.style, leftPanel);
moneyText.TextGetter = GetMoney;
GUIButton button = new GUIButton(new Rectangle(0, 60, 100, 30), "Map", null, Alignment.Left, GUI.style, leftPanel);
GUIButton button = new GUIButton(new Rectangle(0, 70, 100, 30), "Map", null, Alignment.Left, GUI.style, leftPanel);
button.UserData = PanelTab.Map;
button.OnClicked = SelectRightPanel;
button = new GUIButton(new Rectangle(0, 100, 100, 30), "Crew", null, Alignment.Left, GUI.style, leftPanel);
button = new GUIButton(new Rectangle(0, 110, 100, 30), "Crew", null, Alignment.Left, GUI.style, leftPanel);
button.UserData = PanelTab.Crew;
button.OnClicked = SelectRightPanel;
button = new GUIButton(new Rectangle(0, 140, 100, 30), "Location", null, Alignment.Left, GUI.style, leftPanel);
button = new GUIButton(new Rectangle(0, 150, 100, 30), "Hire", null, Alignment.Left, GUI.style, leftPanel);
button.UserData = PanelTab.CurrentLocation;
button.OnClicked = SelectRightPanel;
button = new GUIButton(new Rectangle(0, 190, 100, 30), "Store", null, Alignment.Left, GUI.style, leftPanel);
button.UserData = PanelTab.Store;
button.OnClicked = SelectRightPanel;
//---------------------------------------------------------------
//---------------------------------------------------------------
@@ -65,7 +93,7 @@ namespace Subsurface
Game1.GraphicsWidth - panelRect.Width - 120,
Game1.GraphicsHeight - 80);
rightPanel = new GUIFrame[3];
rightPanel = new GUIFrame[4];
rightPanel[(int)PanelTab.Crew] = new GUIFrame(panelRect, GUI.style);
//rightPanel[(int)PanelTab.Crew].Padding = GUI.style.smallPadding;
@@ -88,14 +116,28 @@ namespace Subsurface
//---------------------------------------
rightPanel[(int)PanelTab.CurrentLocation] = new GUIFrame(panelRect, GUI.style);
//rightPanel[(int)PanelTab.Hire].Padding = GUI.style.smallPadding;
//---------------------------------------
//new GUITextBlock(new Rectangle(0, 0, 200, 25), "Location: ", Color.Transparent, Color.White, Alignment.Left, GUI.style, rightPanel[(int)PanelTab.CurrentLocation]);
rightPanel[(int)PanelTab.Store] = new GUIFrame(panelRect, GUI.style);
selectedItemList = new GUIListBox(new Rectangle(0, 0, 300, 400), Color.White * 0.7f, GUI.style, rightPanel[(int)PanelTab.Store]);
//hireList = new GUIListBox(new Rectangle(0, 30, 300, 0), GUI.style, Alignment.Left, rightPanel[(int)PanelTab.CurrentLocation]);
//hireList.OnSelected = HireCharacter;
var costText = new GUITextBlock(new Rectangle(0, 0, 200, 25), "Cost: ", Color.Transparent, Color.White, Alignment.BottomLeft, GUI.style, rightPanel[(int)PanelTab.Store]);
costText.TextGetter = SelectedItemCost;
buyButton = new GUIButton(new Rectangle(15, 0, 100, 25), "Buy", Alignment.Bottom, GUI.style, rightPanel[(int)PanelTab.Store]);
buyButton.OnClicked = BuyItems;
GUIListBox itemList = new GUIListBox(new Rectangle(0, 0, 300, 400), Color.White * 0.7f, Alignment.TopRight, GUI.style, rightPanel[(int)PanelTab.Store]);
itemList.OnSelected = SelectItem;
foreach (MapEntityPrefab ep in MapEntityPrefab.list)
{
if (ep.Price == 0) continue;
CreateItemFrame(ep, itemList);
}
}
public override void Select()
@@ -117,22 +159,17 @@ namespace Subsurface
new GUITextBlock(new Rectangle(0, 0, 200, 25),
"Location: "+location.Name, GUI.style, rightPanel[(int)PanelTab.CurrentLocation]);
new GUITextBlock(new Rectangle(0, 0, 200, 25),
"("+location.Type+")", GUI.style, rightPanel[(int)PanelTab.CurrentLocation]);
new GUITextBlock(new Rectangle(0, 20, 200, 25),
"("+location.Type.Name+")", GUI.style, rightPanel[(int)PanelTab.CurrentLocation]);
if (location.HireManager != null)
{
hireList = new GUIListBox(new Rectangle(0, 30, 300, 0), GUI.style, Alignment.Left, rightPanel[(int)PanelTab.CurrentLocation]);
hireList.OnSelected = HireCharacter;
hireList = new GUIListBox(new Rectangle(0, 60, 300, 0), GUI.style, Alignment.Left, rightPanel[(int)PanelTab.CurrentLocation]);
hireList.OnSelected = SelectCharacter;
hireList.ClearChildren();
foreach (CharacterInfo c in location.HireManager.availableCharacters)
{
//GUIFrame frame = new GUIFrame(
// new Rectangle(0, 0, 0, 25), Color.Transparent, null, hireList);
//frame.UserData = c;
//frame.Padding = new Vector4(10.0f, 0.0f, 10.0f, 0.0f);
GUITextBlock textBlock = new GUITextBlock(
new Rectangle(0, 0, 0, 25),
c.Name + " (" + c.Job.Name + ")", GUI.style, hireList);
@@ -151,59 +188,8 @@ namespace Subsurface
public override void Deselect()
{
base.Deselect();
//if (previewPlatform != null)
//{
// Game1.World.RemoveBody(previewPlatform);
// previewPlatform = null;
//}
//if (previewHull != null)
//{
// previewHull.Remove();
// previewHull = null;
//}
//if (previewCharacter != null)
//{
// previewCharacter.Remove();
// previewCharacter = null;
//}
}
//private void CreatePreviewCharacter()
//{
// if (previewCharacter != null) previewCharacter.Remove();
// Vector2 pos = new Vector2(1000.0f, 1000.0f);
// previewCharacter = new Character(characterList.SelectedData as CharacterInfo, pos);
// previewCharacter.AnimController.IsStanding = true;
// if (previewPlatform == null)
// {
// Body platform = BodyFactory.CreateRectangle(Game1.World, 3.0f, 1.0f, 5.0f);
// platform.SetTransform(new Vector2(pos.X, pos.Y - 3.5f), 0.0f);
// platform.IsStatic = true;
// }
// if (previewHull == null)
// {
// pos = ConvertUnits.ToDisplayUnits(pos);
// previewHull = new Hull(new Rectangle((int)pos.X - 100, (int)pos.Y + 100, 200, 500));
// }
// Physics.Alpha = 1.0f;
// for (int i = 0; i < 500; i++)
// {
// previewCharacter.AnimController.Update((float)Physics.step);
// previewCharacter.AnimController.UpdateAnim((float)Physics.step);
// Game1.World.Step((float)Physics.step);
// }
//}
public void SelectLocation(Location location, LocationConnection connection)
{
GUIComponent locationPanel = rightPanel[(int)PanelTab.Map].GetChild("selectedlocation");
@@ -227,14 +213,82 @@ namespace Subsurface
{
GUITextBlock textBlock = new GUITextBlock(
new Rectangle(0, 0, 0, 25),
c.Name + " ("+c.Job.Name+")", GUI.style,
c.Name + " (" + c.Job.Name + ")", GUI.style,
Alignment.Left,
Alignment.Left,
characterList);
textBlock.Padding = new Vector4(10.0f, 0.0f, 0.0f, 0.0f);
textBlock.UserData = c;
}
}
private void CreateItemFrame(MapEntityPrefab ep, GUIListBox listBox)
{
Color color = ((listBox.CountChildren % 2) == 0) ? Color.Transparent : Color.White * 0.1f;
GUIFrame frame = new GUIFrame(new Rectangle(0, 0, 0, 50), Color.Transparent, null, listBox);
frame.UserData = ep;
frame.Padding = new Vector4(5.0f, 5.0f, 5.0f, 5.0f);
frame.Color = color;
frame.HoverColor = Color.Gold * 0.2f;
frame.SelectedColor = Color.Gold * 0.5f;
GUITextBlock textBlock = new GUITextBlock(
new Rectangle(40, 0, 0, 25),
ep.Name,
Color.Transparent, Color.White,
Alignment.Left, Alignment.Left,
null, frame);
textBlock.Padding = new Vector4(5.0f, 0.0f, 5.0f, 0.0f);
textBlock = new GUITextBlock(
new Rectangle(0, 0, 0, 25),
ep.Price.ToString(),
null, null,
Alignment.TopRight, GUI.style, textBlock);
if (ep.sprite != null)
{
GUIImage img = new GUIImage(new Rectangle(0, 0, 40, 40), ep.sprite, Alignment.Left, frame);
img.Scale = Math.Min(Math.Min(40.0f / img.SourceRect.Width, 40.0f / img.SourceRect.Height), 1.0f);
}
}
private bool SelectItem(object obj)
{
MapEntityPrefab prefab = obj as MapEntityPrefab;
if (prefab == null) return false;
CreateItemFrame(prefab, selectedItemList);
buyButton.Enabled = gameMode.crewManager.Money >= selectedItemCost;
return false;
}
private bool BuyItems(GUIButton button, object obj)
{
int cost = selectedItemCost;
if (gameMode.crewManager.Money < cost) return false;
gameMode.crewManager.Money -= cost;
for (int i = selectedItemList.children.Count-1; i>=0; i--)
{
GUIComponent child = selectedItemList.children[i];
MapEntityPrefab ep = child.UserData as MapEntityPrefab;
if (ep == null) continue;
gameMode.CargoManager.AddItem(ep);
selectedItemList.RemoveChild(child);
}
return false;
}
public override void Update(double deltaTime)
@@ -267,9 +321,10 @@ namespace Subsurface
if (selectedRightPanel == (int)PanelTab.Map)
{
Game1.GameSession.Map.Draw(spriteBatch, new Rectangle(
rightPanel[selectedRightPanel].Rect.Right - 20 - 400,
rightPanel[selectedRightPanel].Rect.Y + 20,
400, 400));
rightPanel[selectedRightPanel].Rect.X + 20,
rightPanel[selectedRightPanel].Rect.Y + 20,
rightPanel[selectedRightPanel].Rect.Width - 40,
rightPanel[selectedRightPanel].Rect.Height - 150), 3.0f);
}
if (rightPanel[(int)selectedRightPanel].UserData as Location != Game1.GameSession.Map.CurrentLocation)
@@ -281,37 +336,6 @@ namespace Subsurface
spriteBatch.End();
if (characterList.SelectedData != null && selectedRightPanel == (int)PanelTab.Crew)
{
if (previewFrame==null || previewFrame.UserData != characterList.UserData)
{
CharacterInfo previewCharacter = (characterList.SelectedData as CharacterInfo);
GUIFrame frameRoot = new GUIFrame(new Rectangle(350, 30, 300, 500),
new Color(0.0f, 0.0f, 0.0f, 0.8f),
Alignment.Top, GUI.style, rightPanel[selectedRightPanel]);
frameRoot.Padding = new Vector4(20.0f,20.0f,20.0f,20.0f);
previewFrame = previewCharacter.CreateInfoFrame(frameRoot);
previewFrame.UserData = previewCharacter;
}
//if (previewCharacter != null)
//{
// Vector2 position = new Vector2(characterList.Rect.Right + 100, characterList.Rect.Y + 25.0f);
// Vector2 pos = previewCharacter.Position;
// pos.Y = -pos.Y;
// Matrix transform = Matrix.CreateTranslation(new Vector3(-pos + position, 0.0f));
// spriteBatch.Begin(SpriteSortMode.BackToFront, null, null, null, null, null, transform);
// previewCharacter.Draw(spriteBatch);
// spriteBatch.End();
//}
//else
//{
// CreatePreviewCharacter();
//}
}
}
public bool SelectRightPanel(GUIButton button, object selection)
@@ -320,42 +344,7 @@ namespace Subsurface
catch { return false; }
return true;
}
//private void CreatePreviewCharacter()
//{
// if (Game1.Client.Character != null) Game1.Client.Character.Remove();
// Vector2 pos = new Vector2(1000.0f, 1000.0f);
// Character character = new Character(Game1.Client.CharacterInfo, pos);
// Game1.Client.Character = character;
// character.animController.isStanding = true;
// if (previewPlatform == null)
// {
// Body platform = BodyFactory.CreateRectangle(Game1.world, 3.0f, 1.0f, 5.0f);
// platform.SetTransform(new Vector2(pos.X, pos.Y - 2.5f), 0.0f);
// platform.IsStatic = true;
// }
// if (previewPlatform == null)
// {
// pos = ConvertUnits.ToDisplayUnits(pos);
// new Hull(new Rectangle((int)pos.X - 100, (int)pos.Y + 100, 200, 200));
// }
// Physics.Alpha = 1.0f;
// for (int i = 0; i < 500; i++)
// {
// character.animController.Update((float)Physics.step);
// character.animController.UpdateAnim((float)Physics.step);
// Game1.world.Step((float)Physics.step);
// }
//}
private string GetMoney()
{
return "Money: " + ((Game1.GameSession == null) ? "" : gameMode.crewManager.Money.ToString());
@@ -368,17 +357,38 @@ namespace Subsurface
if (Character.Controlled != null && characterInfo == Character.Controlled.Info) return false;
//CreatePreviewCharacter();
if (previewFrame == null || previewFrame.UserData != characterInfo)
{
previewFrame = new GUIFrame(new Rectangle(350, 60, 300, 300),
new Color(0.0f, 0.0f, 0.0f, 0.8f),
Alignment.Top, GUI.style, rightPanel[selectedRightPanel]);
previewFrame.Padding = new Vector4(20.0f, 20.0f, 20.0f, 20.0f);
previewFrame.UserData = characterInfo;
characterInfo.CreateInfoFrame(previewFrame);
}
if (selectedRightPanel == (int)PanelTab.CurrentLocation)
{
GUIButton hireButton = new GUIButton(new Rectangle(0,0, 100, 20), "Hire", Alignment.BottomCenter, GUI.style, previewFrame);
hireButton.UserData = characterInfo;
hireButton.OnClicked = HireCharacter;
}
return false;
}
private bool HireCharacter(object selection)
private bool HireCharacter(GUIButton button, object selection)
{
CharacterInfo characterInfo = selection as CharacterInfo;
if (characterInfo == null) return false;
gameMode.TryHireCharacter(Game1.GameSession.Map.CurrentLocation.HireManager, characterInfo);
if (gameMode.TryHireCharacter(Game1.GameSession.Map.CurrentLocation.HireManager, characterInfo))
{
UpdateLocationTab(Game1.GameSession.Map.CurrentLocation);
}
return false;
}

View File

@@ -43,6 +43,7 @@ namespace Subsurface
button = new GUIButton(new Rectangle(0, 60, 0, 30), "Load Game", Alignment.CenterX, GUI.style, menuTabs[(int)Tabs.Main]);
button.UserData = (int)Tabs.LoadGame;
button.OnClicked = SelectTab;
//button.Enabled = false;
button = new GUIButton(new Rectangle(0, 120, 0, 30), "Join Server", Alignment.CenterX, GUI.style, menuTabs[(int)Tabs.Main]);
button.UserData = (int)Tabs.JoinServer;

View File

@@ -66,6 +66,7 @@
<Compile Include="Characters\AI\SteeringPath.cs" />
<Compile Include="ContentPackage.cs" />
<Compile Include="CoroutineManager.cs" />
<Compile Include="GameSession\CargoManager.cs" />
<Compile Include="GUI\TitleScreen.cs" />
<Compile Include="Items\FixRequirement.cs" />
<Compile Include="Map\Lights\Light.cs" />
@@ -410,6 +411,12 @@
<Content Include="Content\Lights\penumbra.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Content\Map\beaconSymbol.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Content\Map\citySymbol.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Content\Map\iceCrack.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
@@ -422,6 +429,12 @@
<Content Include="Content\Map\locationNames.txt">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Content\Map\militarySymbol.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Content\Map\researchSymbol.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Content\Map\shaft.png">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>

Binary file not shown.