ID:2309333
 
Applies to:
Status: Open

Issue hasn't been assigned a status value.
self-explanatory. I'd rather pre generate icons with maptext on them so i can change or place multiple maptexts on one object using underlays and then save the modified text as an icon, instead of using 5 objects to have text with borders. Then things like creating text with borders would be simple and efficient.

This is what I'm currently doing to achieve text with borders:

/*
var/dmg_amount
To use call: damage_number(src,dmg_amount=50,"#CC66FF")
*/

// hp.Subtract(s)
// damage_number(src,s,"#CC66FF")
proc
damage_number(atom/a,number, color = "#fff", layer = MOB_LAYER + 1, duration = 5, x_add=0, y_add=0)

var/obj/number_obj = a.map_label(number, color, bold = 1, width = 64, layer = layer, xadd = x_add, yadd = y_add)

if(isturf(a))
number_obj.loc = a
else if(istype(a, /atom/movable))
var/atom/movable/m = a

number_obj.loc = m.loc
number_obj.step_x = m.step_x + m.bound_x
number_obj.step_y = m.step_y + m.bound_y

number_obj.pixel_x = a.pixel_x
number_obj.pixel_y = a.pixel_y - 1
number_obj.pixel_z = a.pixel_z

spawn()
sleep(duration * world.tick_lag)

for(var/i = 0 to 12)
number_obj.pixel_z += 3
sleep(world.tick_lag)

del number_obj

atom/proc
map_label(maptext, color = "#fff", bold = 0, layer = MOB_LAYER, width = 32, pixel_x = 0, pixel_y = 0, xadd = 0, yadd = 0)

var/plain_text = maptext
var/pos = findtext(plain_text, "<font")
while(pos > 0)

var/end = findtext(plain_text, ">", pos)

plain_text = copytext(plain_text, 1, pos) + copytext(plain_text, end + 1)

pos = findtext(plain_text, "<font")

if(isnull(plain_text))
plain_text = maptext

bold?(bold="<b>"):(bold = "")


var/obj/o = new()
o.maptext_width = width
o.maptext = "<font color=[color]>[bold][maptext]"
o.layer = layer + 0.1
o.pixel_x = pixel_x
o.pixel_y = pixel_y
o.maptext_x = xadd
o.maptext_y = yadd

var/obj/o1 = new()
o1.maptext = "<font color=#000>[bold][plain_text]"
o1.maptext_width = width
o1.layer = layer
o1.pixel_x = 1
o1.pixel_y = pixel_y
o1.maptext_x = xadd
o1.maptext_y = yadd

var/obj/o2 = new()
o2.maptext = "<font color=#000>[bold][plain_text]"
o2.maptext_width = width
o2.layer = layer
o2.pixel_x = -1
o2.pixel_y = pixel_y
o2.maptext_x = xadd
o2.maptext_y = yadd

var/obj/o3 = new()
o3.maptext = "<font color=#000>[bold][plain_text]"
o3.maptext_width = width
o3.layer = layer
o3.pixel_y = pixel_y
o3.pixel_z = 1
o3.maptext_x = xadd
o3.maptext_y = yadd

var/obj/o4 = new()
o4.maptext = "<font color=#000>[bold][plain_text]"
o4.maptext_width = width
o4.layer = layer
o4.pixel_y = pixel_y
o4.pixel_z = -1
o4.maptext_x = xadd
o4.maptext_y = yadd


o.underlays.Add(o1, o2, o3, o4)
/* o.underlays += o1
o.underlays += o2
o.underlays += o3
o.underlays += o4*/


return o




Mod as you wish.
That's not a border, which is what they're actually talking about, but it does look nice.

For a border, without needing 5 objects, you can do:
        var/obj/o = new()
o.maptext_width = width
o.maptext = "<font color=[color]>[bold][maptext]"
o.layer = layer + 0.1
o.pixel_x = pixel_x
o.pixel_y = pixel_y
o.maptext_x = xadd
o.maptext_y = yadd

var/obj/border = new()
border.maptext = "<font color=#000>[bold][plain_text]"
border.maptext_width = width
border.layer = layer
border.pixel_x = 1
border.pixel_y = pixel_y
border.maptext_x = xadd
border.maptext_y = yadd
var/matrix/M = border.transform
M.Scale(1.1) //1.1x the size of the original
border.transform = M

o.underlays += border

Or, if you're using byond 512 you can do it better:
        var/obj/o = new()
o.maptext_width = width
o.maptext = "<font color=[color]>[bold][maptext]"
o.layer = layer + 0.1
o.pixel_x = pixel_x
o.pixel_y = pixel_y
o.maptext_x = xadd
o.maptext_y = yadd

var/mutable_appearance/border = new(o) //border now looks identical to O, which is *almost* what we want
border.maptext = "<font color=#000>[bold][plain_text]" //set text to black
var/matrix/M = border.transform
M.Scale(1.1) //1.1x the size of the original
border.transform = M

o.underlays += border
In response to CrimsonVision
I believe you are missing a Translate(). I'm wondering how you would go about determining the values (since I think the numbers would be based on the text).
Why would I need to translate it? its location is the exact same place as the original maptext, so when it's scaled by 1.1 it sticks out on all edges, avoiding needing to use 4 pixel offset/matrix translated objects to make each of the 'sides'.
In response to CrimsonVision
It's misaligned. Try it. Comes off as a drop shadow instead of a border.
I have before, I'm not able to check it at the moment, but I can do so once I get home later today.

If it is misaligned, it can't be that major a mistake.
Do you have a picture?
Ah, yes I get what you mean, you do need to offset it back slightly so that it remains centered on the original origin, sorry about that.
In response to CrimsonVision
It's all good.

I'm not sure a proper re-alignment is possible though. It comes off weird-looking even at the closest values.

513's filters is probably the next best thing [once the clipping bug is fixed].
I'm sure I had it at looking decent at one point in time, though yes filters are a great alternative.
In response to CrimsonVision
Actually, it is a border. It's just offset slightly to the right and down a pixel or two instead of enlarged. I realize in your mind that a border might be something that completely surrounds a text or number--but that's not totally accurate (technicality but yea).

In this instance, I tinkered with all the stuff you all played with above and just settled on this one as the best looking one (for me anyway) -- that's why in my reply I said "mod as you see fit".
If you're using 512 you should use
filters = filter(type="outline",color="#000000",size=1)
for maptext.

This is how I've been doing it.

obj/hud/text
maptext_width = 1024
maptext_height = 64
layer = 30
maptext_x = 4
maptext_y = 4
filters = filter(type="outline",size=1,color="#000000")
proc
UpdateText(t)
maptext = "<font face=LilBits size=3>[uppertext(t)]</font>"
In response to Avidanimefan
I would consider that a shadow :)
But sure, I get you.