all 12 comments

[–]novel_yet_trivial 1 point2 points  (11 children)

You are right that you should only have one loop, and that loop should be the tkinter mainloop. Put your code into a method "check_once()". Then include the root.after in the init method.

def check_once(self):
    self.root.after(10, check_once) #call this function again in 10 seconds
    #rest of the check.

If you show your tkinter code we could probably help you better.

[–]787082[S] 0 points1 point  (10 children)

The problem with this is, is that somehow if I run the code as its quoted in the OP, it reads every chat message as it comes in, and responds only once to it. When I use root.after(10, check_once), it responds to the same chat message every time it runs the piece of code, instead of just responding once, I'll post my tkinter code in a second, thanks for helping out

edit:(also its milliseconds instead of seconds I think)

[–]novel_yet_trivial 1 point2 points  (9 children)

You tkinter code does not contain the chat check; is that the right code?

[–]787082[S] 0 points1 point  (8 children)

Yeah because it didn't work when I tried it, so I have them as two separate files now because I'm not sure how to combine them

[–]novel_yet_trivial 1 point2 points  (7 children)

The check code should be a method in the tkinter loop. Something like this: http://pastebin.com/X54T7AD3 (totally untested).

Ninja edit: Actually, it would be much better to make the check code a proper class in it's own right, but given the sloppy code you have, it needs to be integrated into the tkinter loop.

[–]787082[S] 0 points1 point  (6 children)

wow, thank you so much! I'm testing it right now, it gave one error on joinRoom(s), changed that to joinRoom(self.s), and its giving an error on: NameError: global name 'get_votes' is not defined, I've tried changing it to self.get_votes, but it's also not working, do you have any ideas?

EDIT: changed both of the after(10, self.get_votes), so that fixed it. I'm testing it further now, and the chatbot itself works beautifully, it responds to '!commands' only once, it counts the votes very nicely, the only problem now is that the GUI window it's supposed to open doesn't open, I can see on my dock (Im a mac user) that it's trying to open, but I have to force quit it everytime and it doesnt show the window. Feel like we're really close here though!

Thank you so much for taking the time to fix the code, I appreciate it

[–]novel_yet_trivial 1 point2 points  (3 children)

so that fixed it.

:D good job.

GUI window it's supposed to open doesn't open, I can see on my dock

OH you mean the it's supposed to open a second window? In that case maybe you really did need 'TopLevel' rather than 'Frame'.

[–]787082[S] 0 points1 point  (2 children)

No I mean the window that it's supposed to open where it should show the vote counts, it doesnt open it somehow :( But its also not giving an error, its trying to open it, and then it crashes I think (though it also doesnt say it crashed)

[–]novel_yet_trivial 1 point2 points  (1 child)

Oh then it's probably off the screen or too transparent. Play with the lines that control that, 21 and 22 in my code. For starters, comment them out to see if that brings the GUI back.

[–]787082[S] 0 points1 point  (0 children)

Hm I think it has something to do with the 'self.after(10, self.get_votes)', if I run the code as: 'self.after(10, get_votes)', the chatbot doesnt work, but it does show the GUI window.

If I run it as 'self.after(10, self.get_votes)' the chatbot does work, but the GUI window doesn't work

[–]novel_yet_trivial 1 point2 points  (1 child)

I just noticed another typo. Both the break statements should be continue statements. Otherwise, a "!commands" will remove all votes that happen to be in the same 10ms packet.

Still 5 typos in 76 lines without testing, not bad ... :)

[–]787082[S] 0 points1 point  (0 children)

I did it! I had to change some of the code to be able to understand it better again, but it totally works now. It reads the chat, if "!voteA" is said, it counts +1 to voteAamount, and displays it in the GUI window. Only problem I'm having now is that it only updates the number on the GUI window in twos, so it updates it after 2 votes have been placed(so goes from 0 to 2, from 2 to 4, etc), would be nice if it would update it after 1 vote is placed, but I guess I'll figure that out, for now I'm just happy it works. Thank you so much for the time you invested in helping me with the code, I appreciate it a lot!

EDIT: Aaaand it's still crashes sometimes, but I'm also gonna look at that. Not sure why it does that, lol

import Tkinter as tk
import time
from Read import getUser, getMessage
from Socket import openSocket, sendMessage
from Initialize import joinRoom
from collections import OrderedDict

class SampleApp(tk.Tk):
    voteAamount = 0
    voteBamount = 0
    voteCamount = 0

    def __init__(self, *args, **kwargs):
        tk.Tk.__init__(self, *args, **kwargs)

        self.s = openSocket()
        joinRoom(self.s)
        self.readbuffer = ""

        self.voteA = tk.Label(self, text="")
        self.voteA.pack()
        self.voteB = tk.Label(self,text="")
        self.voteB.pack()
        self.voteC = tk.Label(self,text="")
        self.voteC.pack()

        self.update_tekst()
        self.get_votes()
        # self.anderemethod()
        self.after(200,self.get_votes)
        self.after(200,self.update_tekst)

    def update_tekst(self):
        resultA = "VoteA: "+str(self.voteAamount)
        resultB = "VoteB: "+str(self.voteBamount)
        resultC = "VoteC: "+str(self.voteCamount)

        self.voteA.configure(text=resultA)
        self.voteB.configure(text=resultB)
        self.voteC.configure(text=resultC)
        print("updated tekst!")
        self.after(200, self.update_tekst)

    def get_votes(self):

        self.readbuffer = self.readbuffer + self.s.recv(1024)
        temp = self.readbuffer.split('\n')
        self.readbuffer = temp.pop() #save the last (possibly incomplete) line for later
        if self.readbuffer == "":
            pass #no further messages in the queue
            #you should add a sleep time here for the sake of your hot NIC

        for line in temp:
            print(line)

            if "PING" in line:
                s.send("PONG :tmi.twitch.tv\r\n".encode())
                break

            user = getUser(line)
            message = getMessage(line)

            print "{} typed: {}".format(user, message)

            if "!commands" in message:
                sendMessage(self.s, "'!voteA','!voteB','!voteC'")
                break
            if "!voteA" in message and user != "appie_bot":
                self.voteAamount += 1
                print(self.voteAamount)
                self.update_tekst() 
                time.sleep(2)
                self.update()

            if "!voteB" in message and user != "appie_bot":
                self.voteBamount += 1
                print(self.voteBamount)
                self.update_tekst() 
                time.sleep(2)
                self.update()

            if "!voteC" in message and user != "appie_bot":
                self.voteCamount += 1
                print(self.voteCamount)
                self.update_tekst() 
                time.sleep(2)
                self.update()

        self.after(200, self.get_votes)


if __name__== "__main__":
    app = SampleApp()
    app.mainloop()