Почему интерпретируемый порядок отличается от того, что я ожидаю?
У меня есть проблема, с которой я не сталкивался раньше:
Кажется, что порядок интерпретации в моей программе несколько отличается от того, что я ожидаю. Я написал небольшой клиент Twitter. Моя программа действительно публикует твит после того, как я нажму кнопку "GO" (которую также можно активировать, нажав ENTER на клавиатуре). Я не хочу нажимать несколько раз в течение этого периода времени, думая, что я не нажимал его в первый раз. Поэтому, когда кнопка нажата, я бы хотел, чтобы текст метки отображал что-то, что говорит мне, что кнопка была нажата.
Я реализовал это сообщение, изменив текст метки перед отправкой твита. Однако по какой-то причине сообщение не отображается, пока не будет предпринята попытка твита. Но так как у меня есть сообщение с подтверждением после твита, я никогда не вижу это сообщение, и моя первоначальная проблема остается нерешенной.
Я был бы очень признателен за любую помощь. Вот соответствующий код:
class SimpleTextBoxForm(Form):
def __init__(self):
# set window properties
self.Text = "Tweeter"
self.Width = 235
self.Height = 250
#tweet away
self.label = Label()
self.label.Text = "Tweet Away..."
self.label.Location = Point(10, 10)
self.label.Height = 25
self.label.Width = 200
#get the tweet
self.tweetBox = TextBox()
self.tweetBox.Location = Point(10, 45)
self.tweetBox.Width = 200
self.tweetBox.Height = 60
self.tweetBox.Multiline = True
self.tweetBox.WordWrap = True
self.tweetBox.MaxLength = 140;
#ask for the login ID
self.askLogin = Label()
self.askLogin.Text = "Login:"
self.askLogin.Location = Point(10, 120)
self.askLogin.Height = 20
self.askLogin.Width = 60
self.login = TextBox()
self.login.Text= ""
self.login.Location = Point(80, 120)
self.login.Height = 40
self.login.Width = 100
#ask for the password
self.askPass = Label()
self.askPass.Text = "Password:"
self.askPass.Location = Point(10, 150)
self.askPass.Height = 20
self.askPass.Width = 60
# display password box with character hiding
self.password = TextBox()
self.password.Location = Point(80, 150)
self.password.PasswordChar = "x"
self.password.Height = 40
self.password.Width = 100
#submit button
self.button1 = Button()
self.button1.Text = 'Tweet'
self.button1.Location = Point(10, 180)
self.button1.Click += self.update
self.AcceptButton = self.button1
#pack all the elements of the form
self.Controls.Add(self.label)
self.Controls.Add(self.tweetBox)
self.Controls.Add(self.askLogin)
self.Controls.Add(self.login)
self.Controls.Add(self.askPass)
self.Controls.Add(self.password)
self.Controls.Add(self.button1)
def update(self, sender, event):
if not self.password.Text:
self.label.Text = "You forgot to enter your password..."
else:
self.tweet(self.tweetBox.Text, self.login.Text, self.password.Text)
def tweet(self, msg, login, password):
self.label.Text = "Attempting Tweet..." # this should be executed before sending the tweet is attempted. But this seems to be executed only after the try block
try:
success = 'Tweet successfully completed... yay!\n' + 'At: ' + time.asctime().split()[3]
ServicePointManager.Expect100Continue = False
Twitter().UpdateAsXML(login, password, msg)
except:
error = 'Unhandled Exception. Tweet unsuccessful'
self.label.Text = error
else:
self.label.Text = success
self.tweetBox.Text = ""
1 ответ
Порядок интерпретации / выполнения правилен, но в действительности вы не предоставляете Windows Forms время, чтобы изменить текст метки, прежде чем переходить к блокирующему веб-запросу. По сути, установка метки. Текст отправляет сообщение в форму с просьбой изменить текст, но оно не будет выполнено до тех пор, пока вы не вернетесь из обработчика событий (и форма снова не начнет пересылать сообщения). В настоящий момент вы не возвращаетесь из обработчика событий до тех пор, пока веб-запрос не будет завершен, и в этот момент (а) сообщение не имеет значения и (б) метка. Текст мгновенно перезаписывается при следующем обновлении в очереди,
Решение состоит в том, чтобы выполнить запрос веб-службы в фоновом потоке, например, с помощью компонента BackgroundWorker. Это позволяет форме немедленно начать пересылку сообщений, пока работает фоновый поток, поэтому метка будет обновлена немедленно. Тем не менее, обратите внимание, что это также означает, что остальная часть формы будет отзывчивой, что означает, что пользователь может снова нажать кнопку, поэтому вы можете захотеть отключить что-либо, а также просто обновить статус.