#(moepius) How can I highlight certain keywords in chat but leave the prefix or suffix of the word

82 messages · Page 1 of 1 (latest)

feral needle
#

A bit hard to phrase this in english for me, but I hope you'll understand what I'm trying to do.
This script is a part of my chat handler https://paste.denizenscript.com/View/114897. It highlights every keyword I have defined in lists with color or other stuff, if the message contains a keyword.

At the end, I have a choose command where I do specific commands/hovers for different keywords I defined in a list.
The goal is to have words like rules, support, etc. be highlighted in chat and also have a command run when clicked.
Right now this works fine BUT in german you can conjugate words to act as verbs, which lets them end with an "en". So I want to highlight the word "support" when someone writes the word support as is in the chat, but not if it is part of another word that got conjugated or sth. (like in supportING, or supprtEN). This problem also applies to the other tests where I find matches to player names, or server locations.

So TL;DR my keywords should only be highlighted if they begin with a space and end with a space OR if they end with punctuations like ?,:!,etc.
Example:
someword abcdefKEYWORDblabla someword. - should not be highlighted
someword KEYWORD someword - should be highlighted
someword KEYWORD! - should be highlighted (but only the keyword, not the exclamation mark)
someword !KEYWORD someword - should not be highlighted

rapid irisBOT
#

(moepius) How can I highlight certain keywords in chat but leave the prefix or suffix of the word

rapid irisBOT
#

Hi I'm AutoThreadBot! Don't mind me, I'll just be adding the helper team to this thread so they can see it. A human will get to you soon.

radiant notch
#

this might be possible with regex. there is maybe a way to do this nicer with denizen string stuff, but i'm not too sure and it sounds very very complicated to me. someone else could probably find a better way but regex sounds like the best way to me.

#

this is just a quickly thrown together thing but something like this \b(?<!!|\?)KEYWORD seems to do what you want

#

again, it could be possible with normal denizen text manipulation but just wanted to give another option

feral needle
#

And yes, maybe someone has a better solution for this. I will leave this open for now ^^

chilly marsh
#

thats easy

#

you already looping through a list of words (context.message.split)

#

so you could just check if the word starts with your words

#

and if true color it

#

!t element.starts_with

runic gazelleBOT
chilly marsh
#

you might need an additional check for the length of the element, to make sure it doesn't has a weird 'en' ending

#

if the word typed in chat is longer than your word + 1, do not highlight it

feral needle
# chilly marsh so you could just check if the word starts with your words

With "words" you mean I can check with starts_with if my argument from context.message.split starts with a word from the lists I have defined?

On line 18 with- if <[linkstart].filter_tag[<[arg].starts_with[<[filter_value]>]>].any> || <[linkend].filter_tag[<[arg].ends_with[<[filter_value]>]>].any>: I thought I already did sth. like this, but I can still apply some nonsense before the argument and it will geht highlighted ... like xyzwww.website.com will be underlined when testing.

Hm, and right now I go through each list seperatly, not using context.message.split everywhere

chilly marsh
feral needle
#

Is this what you meant?

feral needle
chilly marsh
#

You technically don't need that if, if you do just an element.replace

#

since replace text does simply what it says

#

basically what youre doing is to check if such a word exists, before you replace that word

feral needle
chilly marsh
#

if list1 contains arg

#

or starts with

#

whatever fits ya logic better

feral needle
chilly marsh
#

need an additonal check either way

feral needle
chilly marsh
#

You have too many filter tags

chilly marsh
#

You already filter 6x times for each word a player says

#

can have a map with the key being the word you'd want to replace

#

and the value being the value you'd want to replace with

feral needle
chilly marsh
#

something like

# Script sample
- definemap words:
    Discord: <&color[#5865F2]>Discord<&co> <&n>https://is.gd/cdiscord<&r>
    word: value
- foreach <context.message.split> as:word:
  - foreach <[words].keys> as:replaceable:
    - if <[word].substring[0,<[replaceable].length>]> == <[replaceable]>:
      - Element.replace[<[word].substring[0,<[replaceable].length>]>].with[<[words.<[replaceable]>]>]>
      - foreach stop
#

that should do?

#

!t element.substring

runic gazelleBOT
feral needle
feral needle
# chilly marsh something like ```yaml # Script sample - definemap words: Discord: <&color[...

So in this version I use a map: https://paste.denizenscript.com/View/114918
two things I noticed:

  1. The list of keywords will make my map with the current formatting long af, is there some way to make it more compact? I have many words that will result in the same color highlighting, so it would be nice to be able to bundle them together under one key with one value or sth. like that
  2. When I test for the word ending with a symbol (- define symbols <list[?|,|:|;|!|.]>), I test if the last letter of the word ends with one of the symbols and then I want the last occurence of that symbol to be replaced with the standard color ... problem is that it currently replaces all occurences of the symbol to be replaced ... has the replace tag some sort of index function where I can determine that only the last found matching symbol is replaced? When I give ".last" a number like ".last[2]" it does the opposite of what I want, returning the first 2, but I want only the last
chilly marsh
#

What's the goal of 2

#

What's the purpose of line 20

#

!disablereplies

runic gazelleBOT
chilly marsh
#

for 1, you could have a data script and store it somewhere else

#

If you want to keep everything else default color you can use

#

!t element.color

runic gazelleBOT
# chilly marsh !t element.color

Makes the input text colored by the input color. Equivalent to "<COLOR><ELEMENT_HERE><COLOR.end_format>"
Color can be a color name, color code, hex, or ColorTag... that is: ".color[gold]", ".color[6]", and ".color[#AABB00]" are all valid.
Note that this is a magic Denizen tool - refer to !language Denizen Text Formatting.

Group

text manipulation

Returns

ElementTag

chilly marsh
#

!t element.custom_color

runic gazelleBOT
# chilly marsh !t element.custom_color

Makes the input text colored by the custom color value based on the common base color names defined in the Denizen config file.
If the color name is unrecognized, returns the value of color named 'default'.
Default color names are 'base', 'emphasis', 'warning', 'error'.
Note that this is a magic Denizen tool - refer to !language Denizen Text Formatting.

Group

text manipulation

Returns

ElementTag

chilly marsh
#

that one

#

so if you have "<green>Hello <element[World].custom_color[emphasis]>! What's up?“

#

only the word „World“ will be emphasis

#

everything else stays green

feral needle
# chilly marsh What's the goal of 2

The goal of 2. is that when I have a keyword like "hello.com" or "word" and it only highlights the keyword itself as intended, I want an exception for symbols that commonly are at the end of a sentence or used without a space like colons. So as result the keyword gets highlighted but the symbol does not. On line 20 I test if the current word ends with one of the symbols I defined in a list.

feral needle
feral needle
# chilly marsh so if you have "<green>Hello <element[World].custom_color[emphasis]>! What's up?...

Used this now in a new version: https://paste.denizenscript.com/View/114964
For links I didn't find a good solution, since I need to test if a word is a link in general (starts with www, etc. or ends with .com, .net, etc.), so I didn't know how to use a map for this to be able to only highlight the link itself and don't highlight symbols like ?,!,:,etc. at the end

#

This test did not work

- if <[symbols].filter_tag[<[word].ends_with[<[filter_value]>]>].any>: - define textrpl <[textrpl].replace[<[word].to_list.last>].with[<&f><[word].to_list.last><&r>]>

I thought when I only tried to replace the last letter of the word by converting it to a list, it would only replace the color of the last letter in the word, but when it founds a dot in betwenn it also resets

chilly marsh
#

A link doesnt necessarily ends with .de/.at or whatever

feral needle
chilly marsh
#

you could them detect the same way as you do with replaceables

#

if it starts with http:// its a link and ends with space

#

or https://

#

i can replace meta with whatever i want

feral needle
#

I would have to define what a valid link in general is ... I guess testing for starts_with https://,http:// and www. is good enough ^^

chilly marsh
#

well you could check the top level domain after last dot

#

if the string after last dot starts with com / de / at its a link

feral needle
#

Oh, yes that should work ... only have to make a list of what top-level domains are valid ^^

#

or data script

feral needle
chilly marsh
feral needle
chilly marsh
#

!tias

runic gazelleBOT
# chilly marsh !tias
Info: tias

Try it and see!

If somebody pulled this up for you, you're probably asking a question of the public channel that's easier and faster to figure out by just attempting your idea in-game and looking at the result of that attempt.

feral needle