My discussion about taking my mods "to the next level"

Discussion in 'Mod Discussions' started by killerkiwijuice, March 11, 2015.

  1. killerkiwijuice

    killerkiwijuice Post Master General

    Messages:
    3,879
    Likes Received:
    3,597
    herro again

    This time I would like to convert chat messages into a picture like Twitch chat (or even the forum software :D :) ) does when you type something like "Kappa", it will convert it to [​IMG]

    So far i've gotten this. It doesn't work, and I know the .replace will only replace something like
    Code:
    :) not :)"
    Code:
    switch (self.message) {
      case "Kappa":
        self.message.replace(function() {
          return '<img src="http://vsmallfires.files.wordpress.com/2013/05/kappa.png?w=740" />'
        });
        break;
      case "PogChamp":
        self.message.replace(function() {
          return '<img src="http://static-cdn.jtvnw.net/emoticons/v1/88/1.0" />'
        });
        break;
    };
    I also know that if the message contains a face, the ENTIRE text will be converted to the picture... right?

    I've read up some stuff on Regular Expressions, they make no sense at all. I looked at this though
    http://stackoverflow.com/questions/3055515/replace-a-list-of-emoticons-with-their-images

    Would anyone like to help? :D
  2. wondible

    wondible Post Master General

    Messages:
    3,315
    Likes Received:
    2,089
    The question is do you want to replace the entire message? I'm guessing not, but do correct me. Without trying a mod myself, it's going to look something like this:

  3. killerkiwijuice

    killerkiwijuice Post Master General

    Messages:
    3,879
    Likes Received:
    3,597
    Well if I type something like " gg Kappa " then i would not want the gg to get combined into the picture. Although at this point I can't get it to show up at all.

    Code:
    switch (self.message) {
      case "Kappa":
        self.message = self.message.replace("Kappa", '<img src = "https://encrypted-tbn2.gstatic.com/images?q=tbn:ANd9GcTFnrYIOTTEq8KmBOprA0aiRGn-Dz5K_r1TRkAxPEwsy9GPzTMaNGGArg" />');
        break;
      case "PogChamp":
        self.message = self.message.replace("PogChamp", '<img src = "http://static-cdn.jtvnw.net/emoticons/v1/88/1.0" />');
        break;
    }
    This does not work :(
  4. crizmess

    crizmess Well-Known Member

    Messages:
    434
    Likes Received:
    317
    Hey Kiwi,

    In most programming languages (and javascript isn't any exception here) a switch statement looks something like this:
    Code:
    switch(expression) {
      case n:
        code block
        break;
      default:
        default code block
    }
    
    This means you take that expression that is written behind the switch keyword and evaluate it, then whatever this expression returns will be matched with every case clause, starting with the first one. When a matching clause is found you start to execute the code from that point on, until you reach a break.

    In your example the expression is "self.message", this will usually evaluate to your message string. To stay in your example this would be a string "gg Kappa".
    Then this string is matched against all case clauses, the first one you wrote down is "Kappa". The problem here is, this is not pattern matching, this is a "strict" comparison. And strictly speaking "gg Kappa" is NOT "Kappa". The fact that there is a partial match doesn’t count!
    So the next thing is to check the second case clause - but you guessed it this doesn't match either. Ans since you didn't define any default clause (this is a clause that is executed when no other clause did match up) you just continue without any clause being executed.
    If you want some more detailed information on the switch statement, look here.

    So this isn't what you want. But there is hope: replace
    In the most basic form this looks like this:
    Code:
    string.replace(searchvalue,newvalue)
    
    This construct is a method call. The dot (before the replace) means that this function is called on the object (here called string - for maximal confusion). When this method gets called it replaces all occurrences of searchvalue with the new newvalue and returns that new string.

    In your case @wondible told you the correct solution.
    "self.message" is a string object, on which you can call the replace method to replace all "Kappa"s with an URL or something else. Note that this method returns the new string, it does not alter the old one, so you need to assign the new string back to "self.message".
    That looks something like this:
    Code:
    self.message = self.message.replace("Kappa", 'kappaurl');
    
    But this can go even further! The object returned by replace is a string object, so this object has a replace on itself. So basically we can call replace on the result of a replace. And this looks like:
    Code:
    self.message = self.message.replace("Kappa", 'kappaurl').replace("PogChamp", 'pogchampurl');
    
    Note that there is a dot between the "replace(..)" and the next replace, this indicates a method call. Those chained method calls are called from left to right, which means that the left one (Kappe here) is the inner one that gets called first.
    You can find information about String.replace here.

    BTW: W3Schools has this try-yourself button, where you can test the displayed example - and even try your own code.
    If you want to try some more complex examples (with jQuery ans CSS), I found JSFiddle very helpful (but this was a few years ago, which in IT terms is ages ago).
  5. killerkiwijuice

    killerkiwijuice Post Master General

    Messages:
    3,879
    Likes Received:
    3,597
    yeah, but...

    Why doesn't that work in game? I added a console.log command to the mod (to make sure it parses) and it doesn't show in the debugger, maybe that's a clue... but all of the paths are correct and the .js is valid.

    I changed it to be a new_game.js mod, since starting a game takes too much time.

    Attached Files:

  6. DeathByDenim

    DeathByDenim Post Master General

    Messages:
    4,328
    Likes Received:
    2,125
    Uhm, I just extracted your mod, enabled it in PAMM (well, my launcher, but same thing) and it shows the console.log statements just fine in the Coherent debugger. So you either forgot to enable it, or you aren't looking at the correct scene in the debugger ("Game Lobby").

    edit: by the way,you probably want to rewrite the message handler to intercept and change the messages, this one:
    Code:
      handlers.chat_message = function (msg) {
      model.chatMessages.push(new ChatMessageViewModel(msg.player_name, 'lobby', msg.message));
      };
    
    killerkiwijuice likes this.
  7. killerkiwijuice

    killerkiwijuice Post Master General

    Messages:
    3,879
    Likes Received:
    3,597
    Yeah, I restarted my PC and now they appear in the console... I swear i'm not crazy xD

    Also, I've never really learned about handlers (if I have, I didn't know they were called that), so i'm not quite sure what that code snippet does yet (i copied it into the mod .js and now the chat box is broken... I see the same definition was on line 1924 in new_game.js anyway)

    Error:
    Code:
    Uncaught ReferenceError: ChatMessageViewModel is not defined
    handlers.chat_message
    handlers.chat_message                                                       new_game_public_bot.js:33
    read_message                                                                        common.js:912
    process_message                                                                  common.js:934
    (anonymous function)
    Emitter.trigger
    (anonymous function)
  8. DeathByDenim

    DeathByDenim Post Master General

    Messages:
    4,328
    Likes Received:
    2,125
    Well, I'm not sure what you did, but you probably made a syntax error or something. Though it may just be incompatibility with wondible server help mod? I don't recognize the new_game_public_bot.js file.

    In any case, try just this and only this in your new_game.js:
    Code:
    (function() {
       var old_chat_message_handler = handlers.chat_message;
       handlers.chat_message = function (msg) {
         msg.message = "KAAAAAHN!";
         old_chat_message_handler(msg);
       };
    })();
    
    What handlers do, is handle messages from the engine. In the js files in PA, they are always defined just before the loadMods statement so you can override them. Notice how I saved the original handler and then defined a new one that calls the old one at the end after modifying the message. That way it stays compatible with other mods and it also decreases the changes of the mod breaking after a PA update.

    Oh, and the "(function() {" thing is just so that any variables I declare remain local and can't affect other mods, should they choose the same variable names.
    killerkiwijuice likes this.
  9. killerkiwijuice

    killerkiwijuice Post Master General

    Messages:
    3,879
    Likes Received:
    3,597
    Alright I sorta combined that with a switch statement. I'm going to have to figure out why it works inside that function sometime though...
    Code:
    (function() {
       var old_chat_message_handler = handlers.chat_message;
       handlers.chat_message = function (msg) {
         switch (msg.message) {
             case "Kappa":
                 msg.message = msg.message.replace("Kappa", '<img src="https://encrypted-tbn3.gstatic.com/images?q=tbn:ANd9GcSiJ8DzX5XHqNxcexF4IiHb_BYKpqjZXLnYpvnGgCEKjDaAirw6P1yz0A" />');
                 break;
             case "PogChamp":
                 msg.message = msg.message.replace("PogChamp", '<img src="http://elohell.net/public/comments/small/740fcddcbe7c42437e5f735ea80a2d81.jpg" />');
                 break;
         }
         old_chat_message_handler(msg);
       };
    })();
    This returns not a picture, but the actual <img> tag with the URL, which was expected although obviously the real picture would be... better :p

    but yeah I'm still not sure why the switch works inside the code you wrote above, at least it's working though!!! :)
    Now, is it possible for this chatbox to display pictures, orrrrr ?
  10. DeathByDenim

    DeathByDenim Post Master General

    Messages:
    4,328
    Likes Received:
    2,125
    Hmm, I wonder if that's because it's using the text data-bind instead of the html data-bind in new_game.html in PA.
    http://knockoutjs.com/documentation/html-binding.html

    Have fun figuring that out. :)
  11. cola_colin

    cola_colin Moderator Alumni

    Messages:
    12,074
    Likes Received:
    16,221
    The binding of the chat text probably is a text binding. That prevents injection of html. If it would not do that anybody could write a html chat message and load random js scripts into the UI of all players. That was possible in alpha ;)
    So you will need to work around that without breaking it.
    DeathByDenim likes this.

Share This Page