public override void Draw(Renderer renderer) { for (short i = 0; i < 255; i++) { if (Context.Input.IsKeyDown(i)) { _eventList.Add("isKeyDown(\"" + Context.Input.GetKeyNameFromCode(i) + "\")"); } if (Context.Input.IsKeyUp(i)) { _eventList.Add("IsKeyUp(\"" + Context.Input.GetKeyNameFromCode(i) + "\")"); } } _textArea.Text = string.Join("\n", _eventList); _textArea.Draw(renderer); // This is not the most optimized/smart way to do the following operation. It is however the most readable, and this is an example. Vector2 center = renderer.ScreenCenter; Vector2 charSize = _displayFont.MeasureString("S", 40); Vector2 sLocation = new Vector2(center.X - charSize.X, center.Y - charSize.Y); Rectangle sBounds = new Rectangle(sLocation, charSize); sBounds = RenderKey("S", sBounds, renderer); charSize = _displayFont.MeasureString("A", 40); Vector2 aLocation = new Vector2(sBounds.X - charSize.X - 15, sBounds.Y + 10); Rectangle aBounds = new Rectangle(aLocation, charSize); RenderKey("A", aBounds, renderer); charSize = _displayFont.MeasureString("D", 40); Vector2 dLocation = new Vector2(sBounds.X + sBounds.Width + 15, sBounds.Y + 10); Rectangle dBounds = new Rectangle(dLocation, charSize); RenderKey("D", dBounds, renderer); charSize = _displayFont.MeasureString("W", 40); Vector2 wLocation = new Vector2(sBounds.X + 5, sBounds.Y - charSize.Y - 15); Rectangle wBounds = new Rectangle(wLocation, charSize); RenderKey("W", wBounds, renderer); }
// draws city name plates private void DrawCityNamePlates(SpriteBatch sb) { // draw a nameplate for every city the client can see foreach (City city in client.Cities.ToArray()) { // if the city is not on a chached tile, dont draw its name plate if (client.GetCachedTile(city.Location) == null) { continue; } // get the city name RichText lblCityName; if (city.IsCapital) { lblCityName = $"$(capital) {city.Name}".ToRichText(); } else { lblCityName = $"{city.Name}".ToRichText(); } Vector2 lblCityNameMeasure = lblCityName.Measure(); // position the name plate Vector2 tileCentre = camera.ConvertWorldToScreen(boardRenderer.GetTileCentre(city.Location)); int labelWidth = (int)(cityLabelWidth + lblCityNameMeasure.X / 2); Rectangle dest = new Rectangle((int)(tileCentre.X - labelWidth / 2), (int)(tileCentre.Y - boardRenderer.TileHeight * camera.Zoom.Y), labelWidth, cityLabelHeight); Rectangle defDest = new Rectangle(dest.X + dest.Width / 2 - cityDefensePlateWidth / 2, dest.Y - cityDefensePlateHeight, cityDefensePlateWidth, cityDefensePlateHeight); // draw the name plate cityLabelSprite.DrawNineCut(sb, dest); // draw the defense plate cityLabelSprite.DrawNineCut(sb, defDest); // draw population value RichText lblPop = $"{city.Population}".ToRichText(); Vector2 lblPopMeasure = lblPop.Measure(); lblPop.Draw(sb, new Vector2(dest.X + cityPadding + 5, dest.Y + cityPadding + lblPopMeasure.Y / 4)); // draw population bar float popProgress = city.PopulationGorwthProgress; // clamp progress between 0% and 100% if (popProgress > 1f) { popProgress = 1f; } if (popProgress < 0f) { popProgress = 0f; } int popProgBarHeight = (int)Math.Round(dest.Height * popProgress) - cityPadding * 2; Rectangle popProgBar = new Rectangle(dest.X + cityPopBarPosX, dest.Y + dest.Height - cityPadding - popProgBarHeight, cityPopBarWidth, popProgBarHeight); // draw bar back and bar GraphicsHelper.DrawRectFill(sb, new Rectangle(popProgBar.X, dest.Y + cityPadding, popProgBar.Width, dest.Height - cityPadding * 2), Color.DarkGray); GraphicsHelper.DrawRectFill(sb, popProgBar, Color.Green); // draw turns until pop growth value string lblTurnsUntilPopGrowthString = $"{city.TurnsUntilPopulationGrowth}"; if (city.TurnsUntilPopulationGrowth == -2) // -2 means indefinite { lblTurnsUntilPopGrowthString = "-"; } RichText lblTurnsUntilPopGrowth = lblTurnsUntilPopGrowthString.ToRichText(); lblTurnsUntilPopGrowth.Sections.First().Scale = citySubTextScale; lblTurnsUntilPopGrowth.Draw(sb, new Vector2(popProgBar.X + popProgBar.Width, popProgBar.Y + popProgBar.Height - lblTurnsUntilPopGrowth.Measure().Y *citySubTextScale - cityPadding)); // draw the city name lblCityName.Draw(sb, new Vector2(dest.X + dest.Width / 2 - lblCityNameMeasure.X / 2, dest.Y + lblCityNameMeasure.Y / 4)); // draw the city defense value RichText lblDefense = $"$(strength) {city.Defense}".ToRichText(); Vector2 lblDefenseMeasure = lblDefense.Measure(); lblDefense.Draw(sb, new Vector2(defDest.X + defDest.Width / 2 - lblDefenseMeasure.X / 2, defDest.Y + lblDefenseMeasure.Y / 4)); if (city.ProductionQueue.Count > 0) { Production curProd = city.ProductionQueue.First.Value; // draw current production icon Sprite sprite = GetProductionIcon(curProd); Rectangle prodIconDest = new Rectangle(dest.X + dest.Width - dest.Height, dest.Y, dest.Height, dest.Height); sprite.Draw(sb, prodIconDest); // draw current production progress bar float prodProgress = curProd.Progress / (float)curProd.Cost; // clamp progress between 0% and 100% if (prodProgress > 1f) { prodProgress = 1f; } if (prodProgress < 0f) { prodProgress = 0f; } int prodProgBarHeight = (int)Math.Round(dest.Height * prodProgress) - cityPadding * 2; Rectangle prodProgBar = new Rectangle(prodIconDest.X - cityProdBarWidth, dest.Y + dest.Height - cityPadding - prodProgBarHeight, 3, prodProgBarHeight); // draw bar back and bar GraphicsHelper.DrawRectFill(sb, new Rectangle(prodProgBar.X, dest.Y + cityPadding, prodProgBar.Width, dest.Height - cityPadding * 2), Color.DarkGray); GraphicsHelper.DrawRectFill(sb, prodProgBar, Color.Orange); // draw turns until prod done value string lblTurnsUntilProdDoneString = $"{GetTurnsToProduce(city, curProd)}"; if (city.TurnsUntilPopulationGrowth == -2) // -2 means indefinite { lblTurnsUntilPopGrowthString = "-"; } RichText lblTurnsUntilProdDone = lblTurnsUntilProdDoneString.ToRichText(); lblTurnsUntilProdDone.Sections.First().Scale = citySubTextScale; Vector2 lblTurnsUntilProdDoneMeasure = lblTurnsUntilProdDone.Measure(); lblTurnsUntilProdDone.Draw(sb, new Vector2(prodProgBar.X - prodProgBar.Width - lblTurnsUntilProdDoneMeasure.X + cityPadding, prodProgBar.Y + prodProgBar.Height - lblTurnsUntilProdDoneMeasure.Y * citySubTextScale - cityPadding)); } // draw the hp bar above the name plate double hpPercent = city.HP / (double)city.MaxHP; if (true || hpPercent < 1) { int barThickness = 4; // colour the bar based on current hp Color hpBarColor = Color.Green; if (hpPercent <= 0.5) { hpBarColor = Color.Yellow; } else if (hpPercent <= 0.25) { hpBarColor = Color.Red; } // calculate the bar dest based on current hp Rectangle hpBarBackDest = new Rectangle(dest.X, dest.Y - barThickness / 2, dest.Width, barThickness); Rectangle hpBarDest = new Rectangle(dest.X, dest.Y - barThickness / 2, (int)(dest.Width * hpPercent), barThickness); // draw the hp bar GraphicsHelper.DrawRectFill(sb, hpBarBackDest, Color.DarkGray); GraphicsHelper.DrawRectFill(sb, hpBarDest, hpBarColor); } } }