This is a non-trivial merge. My new approach to rendering text has many advantages, but complicates link rendering.
To limit the complications for now, I'm changing behavior slightly. I'm coloring just the underlines and leaving link text the same color as regular text.
OEIR7M74D747NZME7BK6YHKHNBIYLVE6HD7FZN2HITFF7MX4JLUAC 6K5PFF6XBFTM6CXUVVFIH4CQMCMPHTND3ICDMRMNOME5BUBF27NQC KGBSEDPFDYJPBLXQ5KL5DTRUMXPY7DGSSKOUK4DBNSLZMXZAV3LAC I64IPGJXWRTGHHVAYJUBUIWFR4BY6NM5P7TLTV4JOD7K4BVYDECQC V5SYDHPQ7IKNLZZ3NJ24FDW3IG4O23AASLP2DTKOBPWUUZ5KUPOAC BULPIBEGL7TMK6CVIE7IS7WGAHGOSUJBGJSFQK542MOWGHP2ADQQC 6WDBV52ZFEYAUK6L66LDOKJ5JGHP63VY5R4NDOROZDY6HZJF45KAC HALS7E5UGKCP3DFY456F7Z3Y6WNGIABOCV2SHT34D5ZAGNCPV5PQC VG34LDWYWKMKO76MEKWLUV4RGZCY26LZNSGRA5U2EMAYNGB6LGXQC X3F7ECSLGXCH6NBSDIH7LY47I4EG2RR5VFPEMM6ZVDYQIGFID4HQC PFT5Y2ZYGQA6XXOZ5HH75WVUGA4B3KTDRHSFOZRAUKTPSFOPMNRAC 2CK5QI7WA7M4IVSACFGOJYAIDKRUTZVMMPSFWEJTUNMWTN7AX4NAC TGHAJBESCIEGWUE2D3FGLNOIAYT4D2IRGZKRXRMTUFW7QZETC7OAC -- render any link decorationsfor _,link_offsets in ipairs(line_cache.link_offsets) dolocal s,e,filename = unpack(link_offsets)local lo, hi = Text.clip_filename_with_screen_line(line, line_cache, i, s, e)if lo thenbutton(State, 'link', {x=State.left+lo, y=y, w=hi-lo, h=State.line_height, color={1,1,1},icon = icon.hyperlink_decoration,onpress1 = function()run.switch_to_file(filename)end,})end
-- If fragment is a filename relative to the current directory, register-- a button for clicks on it.local filename = rtrim(frag) -- compute_fragments puts whitespace at the endif file_exists(filename) thenlocal filename_text = App.newText(love.graphics.getFont(), filename)button(State, 'link', {x=x,y=y, w=App.width(filename_text), h=State.line_height, color={1,1,1},icon = icon.hyperlink_decoration,onpress1 = function()run.switch_to_file(filename)end,})
-- render fragment
endendfunction Text.populate_link_offsets(State, line_index)local line = State.lines[line_index]if line.mode ~= 'text' then return endlocal line_cache = State.line_cache[line_index]if line_cache.link_offsets thenreturnendline_cache.link_offsets = {}local pos = 1-- try to wrap at word boundarieslocal s, e = 1, 0while s <= #line.data dos, e = line.data:find('%w+', s)if s == nil then break endlocal word = line.data:sub(s, e)if file_exists(word) then--? print('filename:', s, e, word)table.insert(line_cache.link_offsets, {s, e, word})ends = e + 1
-- Intersect the filename between byte offsets s,e with the bounds of screen line i.-- Return the left/right pixel coordinates of of the intersection,-- or nil if it doesn't intersect with screen line i.function Text.clip_filename_with_screen_line(line, line_cache, i, s, e)local spos = line_cache.screen_line_starting_pos[i]local soff = Text.offset(line.data, spos)if e < soff thenreturnendlocal eoffif i < #line_cache.screen_line_starting_pos thenlocal epos = line_cache.screen_line_starting_pos[i+1]eoff = Text.offset(line.data, epos)if s > eoff thenreturnendendlocal loff = math.max(s, soff)local hoffif eoff thenhoff = math.min(e, eoff)elsehoff = eend--? print(s, e, soff, eoff, loff, hoff)return App.width(line.data:sub(1, loff-1)), App.width(line.data:sub(1, hoff))end