Работа с битами переменной 2.0
Любому человеку, изучавшему основы программирования известно, что число в машинном коде представлено в виде нулей и единиц, то есть в двоичной системе счисления. Минимальной единицей информации в компьютере является бит. Бит может быть либо «выключен», при этом его значение равно нулю, либо «включен», тогда его значение равно единице.
Процессор в РС и по сей день используют 32-битную архитектуру (intel и AMD выпускают процессоры с 64-битной архитектурой, но на данный момент операционные системы толком ее не поддерживают). Биты пронумерованы от 0 до 31 справа на лево: 31 30 29 28 27 ………..5 4 3 2 1 0.
К примеру десятичное число 65 будет представлено так: 0000 0000 0000 0000 0000 0000 0100 0001.
Ну что ж вернемся к нашим опкодам.
Наверное многие задавались вопросом, что же это за такие мудреные команды?
0004: $391 = 0 // integer values
. . . .
08BA: set $391 bit 0 - ?
. . . .
08C0: clear $391 bit 0 - ?
. . . .
08B4: test $391 bit 0 - ?
Прировняв переменную $391 к нулю мы, тем самым, установили все 32 бита в ноль.
Следующим опкодом 08BA: set $391 bit 0 мы устанавливаем нулевой бит равным единице, то есть 0000 0000...0000 0001.
В результате в нижнем левом углу экрана появится цифра 1.
Для чего это нужно? Предположим, что переменная $391 у нас будет отвечать за одежду игрока. К примеру нулевой бит имеет отношение к головному убору или прическе, второй – рубашка, третий – штаны и так далее. Либо каждый бит будет отвечать за различные варианты одежды. Тогда
08BA: set $391 bit 0
08BA: set $391 bit 1
08BA: set $391 bit 2
будет означать, что вся эта одежда будет применена к модели игрока.
Перед созданием игрока делаем проверку
00D6: if
08B4: test $391 bit 0
004D: jump_if_false @
тем самым мы проверяем равен ли нулевой бит единице.
Опкод 08C0: clear $391 bit 0 – очищаем нулевой бит переменной, то есть, приравниваем его к нулю.
Для примера рассмотрим такой поток.
create_thread @TEST1
:TEST1
thread 'TEST1'
$391 = 0 // integer values
:TEST1_18
wait 0
if
00E1: key_pressed 0 8 //Group CTRL Forward
jf @TEST1_46
08BA: set $391 bit 0
jump @TEST1_102
:TEST1_46
wait 0
if
00E1: key_pressed 0 9 //Group CTRL back
jf @TEST1_74
08BA: set $391 bit 1
jump @TEST1_102
:TEST1_74
wait 0
if
00E1: key_pressed 0 10 //conversation - no
jf @TEST1_102
08BA: set $391 bit 2
:TEST1_102
wait 0
if
08B4: test $391 bit 0 // проверяем равен ли нулевой bit единице
jf @TEST1_235 //если нет то переходим на следующую метку
Player.SetClothes($PLAYER_CHAR, "PLAYER_TORSO", "TORSO", Torso)
Player.SetClothes($PLAYER_CHAR, "AFRO", "AFRO", Head)
Player.SetClothes($PLAYER_CHAR, "BBSHORTRED", "BOXINGSHORT", Legs)
Player.SetClothes($PLAYER_CHAR, "COWBOYBOOT2", "BIKER", Shoes)
Player.Build($PLAYER_CHAR)
jump @TEST1_510
:TEST1_235
wait 0
if
08B4: test $391 bit 1
jf @TEST1_372
Player.SetClothes($PLAYER_CHAR, "BBJERSEY", "SLEEVT", Torso)
Player.SetClothes($PLAYER_CHAR, "GROOVECUT", "GROOVECUT", Head)
Player.SetClothes($PLAYER_CHAR, "SUIT1TRGANG", "SUIT1TR", Legs)
Player.SetClothes($PLAYER_CHAR, "SHOEDRESSBRN", "SHOE", Shoes)
Player.Build($PLAYER_CHAR)
jump @TEST1_510
:TEST1_372
wait 0
if
08B4: test $391 bit 2
jf @TEST1_510
Player.SetClothes($PLAYER_CHAR, "TSHIRTERISYELL", "TSHIRT", Torso)
Player.SetClothes($PLAYER_CHAR, "WEDGE", "WEDGE", Head)
Player.SetClothes($PLAYER_CHAR, "BBSHORTWHT", "BOXINGSHORT", Legs)
Player.SetClothes($PLAYER_CHAR, "FLIPFLOP", "FLIPFLOP", Shoes)
Player.Build($PLAYER_CHAR)
:TEST1_510
08C0: clear $391 bit 0
08C0: clear $391 bit 1
08C0: clear $391 bit 2
jump @TEST1_18
P.S. Надеюсь после прочитанного появилось представление о работе выше перечисленных опкодов.