An obvious problem I see with your method is that if 2 nicks join the channel close together, the 2nd nick joining causes %mytext to change between the message seen by the 1st nick, causing them to give theh 'wrong' answer.

This example is what I mentioned in my earlier post. You just create a global variable in the editbox:

/set %voicepassword Anything Can Go Here

And it will return a 6-digit number code that is different for each nick, and changes each day at the same time.

Since there are 10^6 possible numbers of this length, it's literally a 1 in a million chance that someone can guess the right number. You can change the '6' to a different number of digits depending on how hard it should be to guess the number, or how easy you want to make it for someone to input the number. It seems like you're wanting to make this easy for people to voice themselves, and I think you'll find that, for the people who are not simply pasting the text back into the query window, it's easier for someone to type a 6-digit number than 4 random letters.

Since you don't need to share the password with anyone, you can change the password any time you wish, and nobody would notice, except that their daily number would change immediately. Someone who knows anyone else's password for any day, or knowing their password for any day other than today would not help them to know what today's password is.

In my codenumber example, it's changing the code daily and at midnight, so if you want the code to change more frequently, change the 86400 to the new number of seconds in the interval. i.e. changing 86400 to 3600 makes it change hourly. If you want the code to change at 14:00 each day, then change the 0*3600 to 14*3600.

Since you don't really care what the password is, I've also included an ON START command that changes the voice password each time you restart mIRC, and an ON CONNECT command that changes the password each time you connect to a specific Network name (change to the correct word). You can alternatively put the SET command into the perform-on-connect settings for the appropriate network.

Setting the password like this will make it hard for someone to guess the password that allows them to know the code number, and changing it like this means it wouldn't work once the password changes. Of course it does sound like you realize that this really isn't a defense against a bot being able to script something to handle this challenge. To handle something like that, you can have a list of challenge question and answers, but that will make things a lot more complicated.

Code
ON *:START:{ set %voicepassword $regsubex($str(x,50),/x/g,$rand(a,z)) }
ON *:CONNECT:{ if ($network == Change_Me) set %voicepassword $regsubex($str(x,50),/x/g,$rand(a,z)) }

alias voicepassword  { return $hotp(%voicepassword $$1, $calc( ($ctime - $timezone + 0*3600) // 86400),sha256,6) }

on *:TEXT:voiceme:?: {
  ;send the message
  .msg $nick Please reply with this text and I will give you voice: voiceme $voicepassword($nick)
}

on *:TEXT:voiceme *:?: {
  if $nick ison #mychan && $nick !isvoice #mychan {

    if ($1 == $voicepassword($nick)) {
      //echo -a nick in channel

      /mode #mychan +v $nick
      .msg $nick Congrats! You have voice (+v) and can chat in channel. 
    }
    else {
      echo -a here is what to do when they give the wrong number
    }

  }
  else {
    //echo -a $nick not in channel
    .ignore -pu300 $nick
  }
}