Еще один подход к возврату значения из асинхронной функции - передать объект, который сохранит результат от асинхронной функции.
Вот пример того же:
var async = require("async");
// This wires up result back to the caller
var result = {};
var asyncTasks = [];
asyncTasks.push(function(_callback){
// some asynchronous operation
$.ajax({
url: '...',
success: function(response) {
result.response = response;
_callback();
}
});
});
async.parallel(asyncTasks, function(){
// result is available after performing asynchronous operation
console.log(result)
console.log('Done');
});
Я использую объект result
для хранения значения во время асинхронной операции. Это позволяет получить результат даже после асинхронного задания.
Я использую этот подход много. Мне было бы интересно узнать, насколько хорошо этот подход работает, когда задействован результат обратно через последовательные модули.
Не может быть более простым, чем это, я думаю ...
Private Sub TextBox1_MouseDown(ByVal Button As Integer, ByVal Shift As Integer, _
ByVal X As Single, ByVal Y As Single)
With TextBox1
.SelStart = 0
.SelLength = Len(.Text)
End With
End Sub
Если вы нажмете на текстовое поле или вкладку в него, он будет делать то, что вы хотите. Чтобы отменить выбор текста, используйте клавиши со стрелками.
Объяснение
Если вы отлаживаете код, вы увидите, что даже если вы сказали .SetFocus
, фокус не находится в текстовом поле , .SetFocus
не работает в TextBox1_Enter()
, и вам нужно сосредоточиться, чтобы остальная часть кода работала. И, следовательно, моя альтернатива ...
Альтернатива
Вам также может понравиться эта версия :) Это преодолевает ограничение использования мыши в TextBox
Dim boolEnter As Boolean
Private Sub TextBox1_Enter()
boolEnter = True
End Sub
Private Sub TextBox1_MouseDown(ByVal Button As Integer, ByVal Shift As Integer, _
ByVal X As Single, ByVal Y As Single)
If boolEnter = True Then
With TextBox1
.SelStart = 0
.SelLength = Len(.Text)
End With
boolEnter = False
End If
End Sub
Попробуйте использовать тот же код с TextBox1_MouseDown
. Он должен работать.
Private Sub TextBox1_MouseDown(ByVal Button As Integer, ByVal Shift As Integer, ByVal X As Single, ByVal Y As Single)
With TextBox1
.SetFocus
.SelStart = 0
.SelLength = Len(.Text)
End With
MsgBox "Text in TextBox1 is selected"
End Sub
Поведение, которое вы пытаетесь реализовать, уже встроено в TextBox
. Когда вы перемещаете мышь над левой стороной текстового поля, указатель мыши укажет вправо. Если вы нажмете, он выберет весь текст в поле. Щелчок в другом месте отменит выбор текста.
Я попробую еще несколько стратегий, чтобы увидеть, могу ли я заставить это работать в одном Sub.
Это несколько улучшает то, что опубликовано @vacip. Преимущество, которое вы получаете, в том, что вам не нужно добавлять отдельный модуль в модуль для каждого нового текстового поля.
Следующий код в пользовательской форме:
'===== User Form Code ========
Option Explicit
Private Sub TextBox1_Enter()
OnTextBoxEnter
End Sub
Private Sub TextBox2_Enter()
OnTextBoxEnter
End Sub
Private Sub TextBox3_Enter()
OnTextBoxEnter
End Sub
следующий код идет в модуле:
'===== Module Code ========
Sub SelectAllText()
SendKeys "{HOME}+{END}", True
End Sub
Sub OnTextBoxEnter()
Application.OnTime Now + 0.00001, "SelectAllText", Now + 0.00002
End Sub
Мне не удалось выделить / выделить текст в событии Enter, поскольку события mousedown и mouseup, следующие после этого, несколько сбрасывают выбор.
Я думаю, что самый правильный способ добиться того, что вы хотите это:
' if you want to allow highlight more then once, reset the variable LastEntered prior to call SelectTboxText:
' LastEntered = ""
' SelectTboxText TextBox2
Dim LastEntered As String
' Button to select Textbox1
Private Sub CommandButton1_Click()
SelectTboxText TextBox1
End Sub
' Button to select Textbox2
Private Sub CommandButton2_Click()
SelectTboxText TextBox2
End Sub
Private Sub TextBox1_MouseDown(ByVal Button As Integer, ByVal Shift As Integer, ByVal X As Single, ByVal Y As Single)
SelectTboxText TextBox1
End Sub
Private Sub TextBox2_MouseDown(ByVal Button As Integer, ByVal Shift As Integer, ByVal X As Single, ByVal Y As Single)
SelectTboxText TextBox2
End Sub
Public Sub SelectTboxText(ByRef tBox As MSForms.TextBox)
If LastEntered <> tBox.Name Then
LastEntered = tBox.Name
With tBox
.SetFocus
.SelStart = 0
.SelLength = Len(.Text)
End With
End If
End Sub
Итак, каждый раз, когда вы хотите программно активировать одно из текстового поля, вы должны вызвать sub SelectTboxText, что на самом деле не раздражает IMO. Я сделал 2 кнопки для этого в качестве примера.
Pff, взял меня некоторое время. На самом деле, ваш код работает, но он выделяет текст до того, как произойдет событие клика. Таким образом, вы щелкаете в ящике, мгновенно переопределяя выбор, созданный кодом. Я использовал отложенный выбор, и он работает, хотя это немного отвратительно ...
Код для текстовых полей:
Private Sub TextBox1_Enter()
Application.OnTime Now + TimeValue("00:00:01"), "module1.SelectText1"
End Sub
Private Sub TextBox2_Enter()
Application.OnTime Now, "module1.SelectText2"
End Sub
Обратите внимание, что он работает даже с {+ TimeValue ("00:00:01")}, но теоретически это может остановить его от работы время от времени. Хм, подумав, просто оставьте это. Я сомневаюсь, что это когда-нибудь вызовет проблему.
Теперь код в модуле1:
Sub SelectText1()
UserForm1.TextBox1.SelStart = 0
UserForm1.TextBox1.SelLength = Len(UserForm1.TextBox1.Text)
End Sub
Sub SelectText2()
UserForm1.TextBox2.SelStart = 0
UserForm1.TextBox2.SelLength = Len(UserForm1.TextBox2.Text)
End Sub
Надеюсь, это тоже сработает для вас. Инертная проблема. :) Приветствия!
используйте этот параметр
Private Sub TextBox1_Enter()
With TextBox2
.ForeColor = vbBlack
.Font.Bold = False
End With
With TextBox1
.ForeColor = vbRed
.Font.Bold = True
End With
End Sub
Private Sub TextBox2_Enter()
With TextBox1
.ForeColor = vbBlack
.Font.Bold = False
End With
With TextBox2
.ForeColor = vbRed
.Font.Bold = True
End With
End Sub