Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions CentrED/Config.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,18 @@

namespace CentrED;

public class ImageOverlaySettings
{
public string ImagePath = "";
public bool Enabled;
public bool DrawAboveTerrain;
public int WorldX;
public int WorldY;
public float Scale = 1.0f;
public float Opacity = 1.0f;
public float Screen = 0.0f;
}

public class ConfigRoot
{
public string ActiveProfile = "";
Expand All @@ -19,6 +31,7 @@ public class ConfigRoot
public string FontName = "ProggyClean.ttf";
public string Language = "English";
public UI.NumberDisplayFormat NumberFormat = UI.NumberDisplayFormat.HEX;
public ImageOverlaySettings ImageOverlay = new();
}

public static class Config
Expand Down
9 changes: 9 additions & 0 deletions CentrED/Data/Languages/Czech.txt
Original file line number Diff line number Diff line change
Expand Up @@ -261,6 +261,15 @@ SMOOTH_EDGE_TOOLTIP=Okraje nastavené šířky budou vyhlazeny podle okolního t
BLEND_FACTOR=Faktor míchání
BLEND_FACTOR_TOOLTIP=Jak moc bychom měli míchat s aktuální nadmořskou výškou terénu?
SNAP_TO_TERRAIN=Přichytit k terénu
IMAGE_OVERLAY_WINDOW=Překrytí obrázkem
IMAGE_OVERLAY_LOAD=Načíst obrázek
IMAGE_OVERLAY_UNLOAD=Uvolnit
IMAGE_OVERLAY_DRAW_ABOVE=Kreslit nad terénem
IMAGE_OVERLAY_POSITION=Pozice (X, Y)
IMAGE_OVERLAY_SCALE=Měřítko
IMAGE_OVERLAY_OPACITY=Průhlednost
IMAGE_OVERLAY_SCREEN=Screen
IMAGE_OVERLAY_SIZE=Velikost (dlaždice)
RADIUS=Poloměr
BRUSH_RADIUS=Poloměr štětce
SAMPLE_RADIUS=Poloměr vzorkování
Expand Down
11 changes: 10 additions & 1 deletion CentrED/Data/Languages/English.txt
Original file line number Diff line number Diff line change
Expand Up @@ -261,11 +261,20 @@ SMOOTH_EDGE_TOOLTIP=Edges of set width will be smoothened according to surroundi
BLEND_FACTOR=Blend factor
BLEND_FACTOR_TOOLTIP=How much should we blend with current terrain altitude
SNAP_TO_TERRAIN=Snap to terrain
IMAGE_OVERLAY_WINDOW=Image Overlay
IMAGE_OVERLAY_LOAD=Load Image
IMAGE_OVERLAY_UNLOAD=Unload
IMAGE_OVERLAY_DRAW_ABOVE=Draw Above Terrain
IMAGE_OVERLAY_POSITION=Position (X, Y)
IMAGE_OVERLAY_SCALE=Scale
IMAGE_OVERLAY_OPACITY=Opacity
IMAGE_OVERLAY_SCREEN=Screen
IMAGE_OVERLAY_SIZE=Size (tiles)
RADIUS=Radius
BRUSH_RADIUS=Brush radius
SAMPLE_RADIUS=Sample radius
SAMPLE_RADIUS_TOOLTIP=How far to look for neighboring tiles when calculating average
STRENGTH=Strength
EDGE_FALLOFF=Edge falloff
FALLOFF_START=Falloff start
FALLOFF_START_TOOLTIP=Percentage of radius where falloff begins
FALLOFF_START_TOOLTIP=Percentage of radius where falloff begins
11 changes: 10 additions & 1 deletion CentrED/Data/Languages/Polski.txt
Original file line number Diff line number Diff line change
Expand Up @@ -261,11 +261,20 @@ SMOOTH_EDGE_TOOLTIP=Krawędzie na wyznaczonej szerokości będą wygładzone do
BLEND_FACTOR=Współczynnik blendu wysokościa
BLEND_FACTOR_TOOLTIP=Jak duży wpływ obecna wysokość terenu ma mieć na wynik operacji
SNAP_TO_TERRAIN=Przyciągnij do terenu
IMAGE_OVERLAY_WINDOW=Nakładka obrazu
IMAGE_OVERLAY_LOAD=Wczytaj obraz
IMAGE_OVERLAY_UNLOAD=Usuń
IMAGE_OVERLAY_DRAW_ABOVE=Rysuj nad terenem
IMAGE_OVERLAY_POSITION=Pozycja (X, Y)
IMAGE_OVERLAY_SCALE=Skala
IMAGE_OVERLAY_OPACITY=Przezroczystość
IMAGE_OVERLAY_SCREEN=Screen
IMAGE_OVERLAY_SIZE=Rozmiar (kafelki)
RADIUS=Promień
BRUSH_RADIUS=Promień pędzla
SAMPLE_RADIUS=Promień próbkowania
SAMPLE_RADIUS_TOOLTIP=Jak daleko szukać sąsiednich kafelków przy obliczaniu średniej
STRENGTH=Siła
EDGE_FALLOFF=Zanikanie krawędzi
FALLOFF_START=Początek zanikania
FALLOFF_START_TOOLTIP=Procent promienia, od którego zaczyna się zanikanie
FALLOFF_START_TOOLTIP=Procent promienia, od którego zaczyna się zanikanie
11 changes: 10 additions & 1 deletion CentrED/Data/Languages/Português.txt
Original file line number Diff line number Diff line change
Expand Up @@ -261,11 +261,20 @@ SMOOTH_EDGE_TOOLTIP=As bordas de largura definida serão suavizadas de acordo co
BLEND_FACTOR=Fator de Mistura
BLEND_FACTOR_TOOLTIP=Quanto devemos misturar com a altitude atual do terreno
SNAP_TO_TERRAIN=Encaixe-o no terreno
IMAGE_OVERLAY_WINDOW=Sobreposição de Imagem
IMAGE_OVERLAY_LOAD=Carregar Imagem
IMAGE_OVERLAY_UNLOAD=Descarregar
IMAGE_OVERLAY_DRAW_ABOVE=Desenhar Acima do Terreno
IMAGE_OVERLAY_POSITION=Posição (X, Y)
IMAGE_OVERLAY_SCALE=Escala
IMAGE_OVERLAY_OPACITY=Opacidade
IMAGE_OVERLAY_SCREEN=Screen
IMAGE_OVERLAY_SIZE=Tamanho (tiles)
RADIUS=Raio
BRUSH_RADIUS=Raio do pincel
SAMPLE_RADIUS=Raio de amostragem
SAMPLE_RADIUS_TOOLTIP=Até onde procurar blocos vizinhos ao calcular a média
STRENGTH=Intensidade
EDGE_FALLOFF=Atenuação de borda
FALLOFF_START=Início da atenuação
FALLOFF_START_TOOLTIP=Porcentagem do raio onde a atenuação começa
FALLOFF_START_TOOLTIP=Porcentagem do raio onde a atenuação começa
9 changes: 9 additions & 0 deletions CentrED/Languages/LangEntry.cs
Original file line number Diff line number Diff line change
Expand Up @@ -265,6 +265,15 @@ public enum LangEntry
BLEND_FACTOR,
BLEND_FACTOR_TOOLTIP,
SNAP_TO_TERRAIN,
IMAGE_OVERLAY_WINDOW,
IMAGE_OVERLAY_LOAD,
IMAGE_OVERLAY_UNLOAD,
IMAGE_OVERLAY_DRAW_ABOVE,
IMAGE_OVERLAY_POSITION,
IMAGE_OVERLAY_SCALE,
IMAGE_OVERLAY_OPACITY,
IMAGE_OVERLAY_SCREEN,
IMAGE_OVERLAY_SIZE,
RADIUS,
BRUSH_RADIUS,
SAMPLE_RADIUS,
Expand Down
143 changes: 143 additions & 0 deletions CentrED/Map/ImageOverlay.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,143 @@
using System.Numerics;
using CentrED.Renderer;
using Microsoft.Xna.Framework.Graphics;
using static CentrED.Constants;

namespace CentrED.Map;

public class ImageOverlay : MapObject
{
public ImageOverlay()
{
for (int i = 0; i < 4; i++)
{
Vertices[i] = new MapVertex(Vector3.Zero, Vector3.Zero, Vector4.Zero, Vector3.Zero);
}
}

private bool _enabled;
private bool _drawAboveTerrain;
private int _worldX;
private int _worldY;
private float _scale = 1.0f;
private float _opacity = 1.0f;
private float _screen = 0.0f;

public bool Enabled
{
get => _enabled;
set => _enabled = value;
}

public bool DrawAboveTerrain
{
get => _drawAboveTerrain;
set => _drawAboveTerrain = value;
}

public int WorldX
{
get => _worldX;
set
{
_worldX = value;
UpdateVertices();
}
}

public int WorldY
{
get => _worldY;
set
{
_worldY = value;
UpdateVertices();
}
}

public float Scale
{
get => _scale;
set
{
_scale = Math.Max(0.1f, Math.Min(10.0f, value));
UpdateVertices();
}
}

public float Opacity
{
get => _opacity;
set
{
_opacity = Math.Max(0.0f, Math.Min(1.0f, value));
for (int i = 0; i < 4; i++)
{
Vertices[i].Hue.Z = _opacity;
}
}
}

public float Screen
{
get => _screen;
set
{
_screen = Math.Max(0.0f, Math.Min(1.0f, value));
for (int i = 0; i < 4; i++)
{
Vertices[i].Hue.Y = _screen;
}
}
}

public int ImageWidth => Texture?.Width ?? 0;
public int ImageHeight => Texture?.Height ?? 0;
public float WidthInTiles => ImageWidth * _scale;
public float HeightInTiles => ImageHeight * _scale;

public void LoadImage(GraphicsDevice gd, string path)
{
UnloadImage();

using var fileStream = File.OpenRead(path);
Texture = Texture2D.FromStream(gd, fileStream);
TextureBounds = new System.Drawing.Rectangle(0, 0, Texture.Width, Texture.Height);
UpdateVertices();
}

public void UnloadImage()
{
if (Texture != null)
{
Texture.Dispose();
Texture = null!;
}
}

private void UpdateVertices()
{
if (Texture == null)
return;

float width = WidthInTiles * TILE_SIZE;
float height = HeightInTiles * TILE_SIZE;
float x = _worldX * TILE_SIZE;
float y = _worldY * TILE_SIZE;

Vertices[0].Position = new Vector3(x, y, 0);
Vertices[0].Texture = new Vector3(0, 0, 0);
Vertices[1].Position = new Vector3(x + width, y, 0);
Vertices[1].Texture = new Vector3(1, 0, 0);
Vertices[2].Position = new Vector3(x, y + height, 0);
Vertices[2].Texture = new Vector3(0, 1, 0);
Vertices[3].Position = new Vector3(x + width, y + height, 0);
Vertices[3].Texture = new Vector3(1, 1, 0);

for (int i = 0; i < 4; i++)
{
Vertices[i].Hue = new Vector4(0, _screen, _opacity, 0);
Vertices[i].Normal = Vector3.Zero;
}
}
}
27 changes: 27 additions & 0 deletions CentrED/Map/MapManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -393,6 +393,7 @@ public static Vector2 ScreenToMapCoordinates(float x, float y)

public StaticsManager StaticsManager = new();
public VirtualLayerObject VirtualLayer = VirtualLayerObject.Instance; //Used for drawing
public ImageOverlay ImageOverlay = new(); //Used for image overlay feature

public void UpdateAllTiles()
{
Expand Down Expand Up @@ -1023,6 +1024,7 @@ public void Draw()
return;

_mapRenderer.SetRenderTarget(null);
Metrics.Measure("DrawImageOverlayBelow", () => DrawImageOverlay(false));
Metrics.Measure("DrawLand", () => DrawLand(Camera, ViewRange));
Metrics.Start("DrawLandGrid");
if (ShowGrid)
Expand All @@ -1032,6 +1034,7 @@ public void Draw()
Metrics.Stop("DrawLandGrid");
Metrics.Measure("DrawLandHeight", DrawLandHeight);
Metrics.Measure("DrawStatics", () => DrawStatics(Camera, ViewRange));
Metrics.Measure("DrawImageOverlayAbove", () => DrawImageOverlay(true));
Metrics.Measure("ApplyLights", ApplyLights);
Metrics.Measure("DrawVirtualLayer", DrawVirtualLayer);
Metrics.Stop("DrawMap");
Expand Down Expand Up @@ -1282,6 +1285,30 @@ public void DrawVirtualLayer()
_mapRenderer.End();
}

public void DrawImageOverlay(bool aboveTerrain)
{
if (!ImageOverlay.Enabled || ImageOverlay.Texture == null)
{
return;
}
if (ImageOverlay.DrawAboveTerrain != aboveTerrain)
{
return;
}
MapEffect.WorldViewProj = Camera.FnaWorldViewProj;
MapEffect.CurrentTechnique = MapEffect.Techniques["ImageOverlay"];
_mapRenderer.Begin
(
MapEffect,
RasterizerState.CullNone,
SamplerState.LinearClamp,
DepthStencilState.None,
BlendState.AlphaBlend
);
_mapRenderer.DrawMapObject(ImageOverlay, Vector4.Zero);
_mapRenderer.End();
}

public bool Export = false;
public string ExportPath = "render.png";
public int ExportWidth = 1920;
Expand Down
34 changes: 31 additions & 3 deletions CentrED/Renderer/Shaders/MapEffect.fx
Original file line number Diff line number Diff line change
Expand Up @@ -173,16 +173,36 @@ PSInput VirtualLayerVSMain(VSInput vin) {
float4 VirtualLayerPSMain(PSInput pin) : SV_Target0
{
//0.7 worked for me as it's not glitching when moving camera
if (abs(fmod(pin.Texture.x, TileSize)) < 0.7 || abs(fmod(pin.Texture.y, TileSize)) < 0.7)
if (abs(fmod(pin.Texture.x, TileSize)) < 0.7 || abs(fmod(pin.Texture.y, TileSize)) < 0.7)
{
return VirtualLayerBorderColor;
}
else
}
else
{
return VirtualLayerFillColor;
}
}

float4 ImageOverlayPSMain(PSInput pin) : SV_Target0
{
float4 color = tex2D(TextureSampler, pin.Texture.xy);

// Hue.y = Screen (makes dark colors more transparent based on luminance)
// Hue.z = Opacity (true uniform transparency for all pixels)
float screen = pin.Hue.y;
float opacity = pin.Hue.z;

// Apply uniform opacity to ALL channels (RGBA) - this fades the entire image
color *= opacity;

// Then apply screen effect - makes dark pixels more transparent based on brightness
float luminance = dot(color.rgb, float3(0.299, 0.587, 0.114));
float screenEffect = lerp(1.0, luminance, screen);
color.a *= screenEffect;

return color;
}

Technique Terrain
{
Pass
Expand Down Expand Up @@ -224,4 +244,12 @@ Technique VirtualLayer {
VertexShader = compile vs_2_0 VirtualLayerVSMain();
PixelShader = compile ps_2_0 VirtualLayerPSMain();
}
}

Technique ImageOverlay {
Pass
{
VertexShader = compile vs_2_0 TileVSMain();
PixelShader = compile ps_2_0 ImageOverlayPSMain();
}
}
Binary file modified CentrED/Renderer/Shaders/MapEffect.fxc
Binary file not shown.
3 changes: 2 additions & 1 deletion CentrED/UI/UIManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,8 @@ public unsafe UIManager(GraphicsDevice gd, GameWindow window, Keymap keymap)
AddWindow(Category.Tools, new ChatWindow());
AddWindow(Category.Tools, new HistoryWindow());
AddWindow(Category.Tools, new ServerAdminWindow());

AddWindow(Category.Tools, new ImageOverlayWindow());

AddWindow(Category.Menu, new MinimapWindow());
DebugWindow = new DebugWindow();

Expand Down
Loading
Loading