..........................................................................
	  ___      _     _       _      _    _    
	//   \\  // \\  | \  || | \  || \\  //  
	\\___   ||___|| ||\\ || ||\\ ||  \\//   
	     \\ ||   || || \\|| || \\||   ||	
	\\___// ||   || ||  \_| ||  \_|   ||    
		  ___                       __      ____   __
		||   \\ ||   || || ||     ||  \\  ||     ||  ||
		||___// ||   || || ||     ||   || ||____ ||_ ||
		||   \\ ||   || || ||     ||   || ||     || \\
		||___//  \\__|| || ||____ ||__//  ||____ ||  \\


..........................................................................

		Содержание:

		1. О программе
		 1.1	Что это такое?
		 1.2	Установка и обновление

		2. Кодинг
		 2.1	Синтаксис
		 2.2	Типы данных
		 2.3	Переменные
		 2.4	Классы
		  2.4.1 Основные понятия
		  2.4.2 Условные команды
		  2.4.3 Процедуры
		  2.4.4 Свойства
		  2.4.5 Члены класса
		  2.4.6 Класс Model
		  2.4.7 Расширенные названия параметров
		 2.5	Циклы
		  2.5.1 Оператор FOR
		  2.5.2 Оператор WHILE
		  2.5.3 Оператор REPEAT
		  2.5.4 Continue и Break
		 2.6	Дополнительные команды
		 2.7	Кейворды
		 2.8	Условия
		 2.9	HEX..END	

		3. Редактор

		4. Поиск опкодов (Opcode Search Tool)

		5. История изменений

		6. Дополнительная информация

..........................................................................


		1. О программе


..........................................................................


		1.1	Что это такое?
..........................................................................

		Sanny Builder - мощнейшее средство для создания новых 
	миссий в линейке трехмерных игр GTA (GTA3, VC, SA). 
	В комплект входит декомпилятор, позволяющий раскомпилировать 
	файлы MAIN.SCM и SCRIPT.IMG (SA), содержащие игровые скрипты; 
	компилятор, и удобный редактор со множеством вспомогательных функций, 
	таких как подсветка синтаксиса,	чтение координат игрока в игре, 
	быстрое перемещение по участкам кода и многое другое. 
	Добавьте к этому быструю скорость работы и настраиваемый синтаксис 
	кода (через классы и ключевые слова) и Вы получите представление 
	о программе.
		Have fun.

..........................................................................

		1.2	Установка и обновление
..........................................................................

		Просто распакуйте архив в удобное для Вас место и
	запустите файл sanny.exe

	Параметры командной строки:
	\sa - использовать как редактор SA (по умолчанию)
	\vc - использовать как редактор VC
	\gta3 - использовать как редактор GTA3

	Свежая версия всегда доступна на веб-страничке программы (см. ниже).



..........................................................................


		2. Кодинг


..........................................................................


		2.1	Синтаксис
..........................................................................

	Информация для тех, кто привык работать с билдером.
	Весь синтаксис команд абсолютно такой же как и в SAMB 0.33, за
	исключением обозначения меток и локальных переменных. 
	Метки начинаются с @, независимо от местоположения в файле. 
	А локальные переменные обозначаются символом @ в конце, а не в 
	начале, как в SaMB.


..........................................................................

		2.2	Типы данных
..........................................................................


	$ - обозначение глобальных переменных. Их значения могут 
	использоваться в любом месте кода. 
		Пример: 0004: $MyVar = 100

	@ - в начале: метка
		Пример: 0002: jump @MyLabel

	  - в конце: локальная переменная. Их значения используются 
	только в пределах одного потока 
		Пример: 0006: 100@ = 10

	'...' - текст (макс. 7 символов). 
	Допускается пустое значение: ''

		Пример: 03A4: name_thread 'MAIN'


	"..." - текст (точный максимум неизвестен, но не больше 255 символов)

	(NEW)
	В данном тексте вы можете использовать специальные символьные
	константы, которые заменяют собой управляющие символы: 
	\n - New Line (заменяет константу ~n~ - переход на новую строку)
	\s - Space (заменяет байт #32 - дополнительный пробел)

	Также вы можете использовать в тексте одинарные кавычки или двойные кавычки.
	Для двойных кавычек необходимо использовать специальный префикс \.

	Допускается пустое значение: ""

		Пример: 0662: write_debug_message "Hello, \"world\"! \n 'Here we go!'"


	s$ - глобальная стринговая переменная
		Пример:	05A9: s$MyString = 'GLOBAL'

	@s - локальная стринговая переменная
		Пример: 05AA: 1@s = 'LOCAL'

	v$ - глобальная стринговая переменная
		Пример: 06D1: v$MyString = "LONG_GLOBAL"

	@v - локальная стринговая переменная	
		Пример: 06D2: 1@v = "LONG_LOCAL"

	# - имя модели из одного из IDE - файлов игры
		Пример: 0247: request_model #CELLPHONE

	& - прямой байтовый адрес (ADMA). 
	Читает и пишет значения по указанному адресу
	Может использоваться в тех же случаях, когда используется тип $.
		Пример: &57 += &120(&231,4i)

	(примечание: этот адрес - локальное смещение внутри файла main.scm,
	 относительно его начала)

	(NEW)
	0x - число в шестнадцатиричном формате.
	-0x - отрицательное значение

		Пример:	0004: $var = -0xBB08

	Число должно быть в интервале -80000000..7FFFFFFF


	См. также:	http://sannybuilder.com/articles/3


..........................................................................

		2.3	Переменные
..........................................................................

	Переменные используются для хранения каких-либо данных.
	Вы можете читать их значения, записывать новые.

	Переменные бывают двух типов: глобальные (их значения доступны
	в любом месте скрипта) и локальные (только в пределах одного
	потока). Обозначения смотрите выше.

	Переменные используются в качестве операндов (членов) математических
	и логических выражений. Sanny Builder позволяет не использовать
	опкоды в подобных выражениях. Например, вы можете писать
	$var = 0 вместо 0004: $var = 0. Во многих случаях это будет
	даже правильнее, потому часто в таких выражениях скриптеры
	используют неверные опкоды.

	Однако, если в выражении в обоих сторон участвуют переменные, то
	компилятор может не знать, какой именно опкод необходим в данном
	случае. Это происходит из-за того, что возможны два варианта:
	если обе переменные типа Integer или типа Float.

	Для того чтобы подсказать компилятору тип переменной, она должна быть
	объявлена через конструкцию VAR..END. Она позволяет объявлять 
	переменные и их типы, для последующего манипулирования ими. 
	Например используйте код

	var
	 $1stIntVar : Integer
	 $2ndIntVar : Integer
	end

	и вы можете использовать их в математических операциях подобно
	$1stIntVar = $2ndIntVar 
	$1stIntVar *= $2ndIntVar и т.д.


	Поддерживаются следующие типы переменных:

	Integer, Int 		- integer values
	Float	     		- floating-points values
	String, ShortString	- Fixed length string variable
	(только для массивов, используйте s$, @s для переменных)
	LongString		- Variable length string variable
	(только для массивов, используйте v$, @v для переменных)

	(При нажатии Ctrl+Space появится список типов)

	Также Вы можете объявлять и массивы. Используется следующая запись:

	var
	 <array name>: array <size> of <type>
	end
	
	Например:

	var
	 $FloatArray: array 10 of Float
	end

	После этого вы можете работать с этим массивом без указания его типа
	и размера. Например:

	$FloatArray[$RndIndex] += 100.0


	Кроме глобальных переменных можно объявлять и локальные переменные.
	Но нужно помнить, что в этом случае все такие переменные во всех 
	потоках будут иметь один и тот же тип. Чтобы избежать этого, вы
	можете переобъявлять переменные в каждом потоке. Например:

	;--------------------
	Thread 'Food'
	Var
	 10@ : Float
	 $Var : Float
	End
	$var = 1
	10@ = $Var
	end_thread
	;--------------------
	Thread 'Loop'
	Var
	 10@ : Int
	 $Var : Int
	End
	$var = 1
	10@ = $Var
	end_thread
	;--------------------

	В первом потоке переменная 10@ будет расцениваться как float,
	во втором - как integer. Вообще вы можете переобъявлять	переменные 
	сколько угодно раз.

	Также вы можете инициализировать значение переменной сразу при объявлении.
	Для этого после указания типа поставьте знак = и стартовое значение:

	var
	 $fVar: float = 1.0
	end

	Переменная $fVar будет запомнена как Float и одновременно
	в SCM будет записан опкод: 0005: $fVar = 1.0

	Инициализация доступна только для переменных, но не массивов!


..........................................................................

		2.4	Классы
..........................................................................


			2.4.1 Основные понятия
..........................................................................

	Sanny Builder допускает использование классов при написании кода.
	Классы - это группа опкодов, относящихся к какому-либо виду
	объектов в игре: игрок, актер, машина и т.д.

	Все классы заранее определены в файле classes.db и изменять их в 
	процессе кодинга невозможно. Все изменения вносятся напрямую в этот
	файл.

	Каждый класс обладает набором команд (опкодов). Их можно разделить 
	на несколько групп:

	- условные
	- процедуры (методы)
	- свойства

..........................................................................

			2.4.2	Условные команды
..........................................................................
	Условные опкоды в списке команд, вызываемом нажатием Ctrl+Space,
	обозначаются словом Check. Чаще всего у них один параметр - это
	хендл (имя) владельца класса: машины, игрока и т.д.
	Например:

	if
	 Player.Defined($PLAYER_CHAR)
	jf @anywhere
..........................................................................

			2.4.3	Процедуры
..........................................................................
	Процедурные опкоды предназначены для выполнения какого-либо 
	конкретного действия в игре: движение объекта, уничтожение его и 
	т.п. Отдельный вид таких опкодов - это конструкторы, которые 
	создают объект (актера, машину)	и возвращают его хендл. В SB 
	конструкторы могут использоваться как процедура, так и как свойство.

	Player.Create($PLAYER_CHAR, #NULL, 2488.5601, -1666.84, 13.38) - процедура
	$PLAYER_CHAR = Player.Create(#NULL, 2488.5601, -1666.84, 13.38) - 
	свойство-конструктор

	Эффект будет одинаков.

..........................................................................

			2.4.4	Свойства
..........................................................................

	Свойства класса используются для чтения или записи каких-либо 
	значений. Например свойство Money класса Player позволяет оперировать 
	с тремя опкодами:

	0109: player $PLAYER_CHAR money += 1000000
	010A:   player $PLAYER_CHAR money > 461@
	010B: 4@ = player $PLAYER_CHAR money

	После того как это свойство описано в файле classes.db вы можете 
	использовать следующие команды:

	player($PLAYER_CHAR).Money += 1000000
	player($PLAYER_CHAR).Money > 461@
	4@ = player($PLAYER_CHAR).Money

	В настоящий момент существует серьезное ограничение по использованию
	свойств в качестве операндов выражений. Sanny Builder может
	скомпилировать только такие выражения, которые заранее прописаны в
	файле classes.db. Т.е. вы не можете, например, использовать такое
	выражение:
	player($PLAYER_CHAR).Money -= 1000000


..........................................................................

			2.4.5	Члены класса
..........................................................................

	Начиная с версии 2.6 также можно инициализировать переменные как
	члены класса и оперировать с ними как с классом. Например:

	var
	 $PLAYER_CHAR: Player
	end

	Мы объявили переменную $PLAYER_CHAR как класс Player. Теперь для
	нее доступны все команды, какие есть для этого класса.
	Например:

	if
	 $PLAYER_CHAR.Defined
	jf @anywhere

	Обратите внимание, что такие переменные будут компилироваться как
	первый параметр, поэтому дублировать ее не следует.

	Player.SetClothes($PLAYER_CHAR, "PLAYER_FACE", "HEAD", Head) 
	=
	$PLAYER_CHAR.SetClothes("PLAYER_FACE", "HEAD", Head)	

	Такие переменные также можно переобъявлять и изменять их тип.

..........................................................................

			2.4.6 Класс Model
..........................................................................
	Класс Model можно использовать при помощи имен моделей, которые
	всегда будут являться членами этого класса. Например, вы можете
	использовать следующий код:

	--------------------------
	#AK47.Load

	:loop
	wait 0
	if
	 #AK47.Available
	jf @loop
	--------------------------

	Это будет тоже самое что

	--------------------------
	Model.Load(#AK47)

	:loop
	wait 0
	if
	 Model.Available(#AK47)
	jf @loop
	--------------------------

..........................................................................

			2.4.7 Расширенные названия параметров
..........................................................................


	В классах вы можете использовать текстовые названия для параметров 
	для повышения читабельности кода.
	
	Например: 
	Player.SetClothes($PLAYER_CHAR, "VEST", "VEST", Torso)

	Torso - это параметр типа Extended.

	Такие параметры реализуются через описание их в файле 'classes.db'.

	Текстовые названия допускаются только для параметров типа Integer.
	При описании параметра сначала указывается имя параметра для значения
	0, затем - для 1 и т.д. Кол-во названий неограниченно.
	
	Перед именами параметров cледует ставить знак ^. Если вы хотите 
	пропустить одно из имен, вставьте вместо него пробел, например:
	"BodyPart: ^Torso^ ^Legs^Shoes". Тогда при декомпиляции в случае, если
	этот параметр будет равен 1, он не будет заменен.

	Также вы можете сами определять значение для параметра, вне зависимости
	от его порядкового номера. Для этото после имени параметра поставьте
	знак = и необходимое значение, например:

	"BodyPart: ^Torso^Head^Legs^Shoes^Special=17"
	Параметр Special будет компилироваться как число 17.

	Для каждого опкода можно использовать только ОДИН расширенный параметр


	Для облегчения использования расширенных названий, их список
	для текущей команды может вызываться нажатием Ctrl+Space.
	Просто установите курсор туда, где должен быть расширенный параметр,
	нажмите ctrl+space и в редакторе появится список возможных имен с
	указанием числового значения для каждого из них.


..........................................................................

		2.5	Циклы
..........................................................................

	В SB используются следующие виды циклов: 

	1. FOR..END
	2. WHILE..END
	3. REPEAT..UNTIL

	Циклы могут быть вложенными (т.е. один цикл внутри другого).

	Внимание: в циклах не используется задержка. Вы должны сами 
	устанавливать ее внутри тела цикла, если она необходима.

..........................................................................

			2.5.1 Оператор FOR..END
..........................................................................
	Этот оператор задает цикл со строго определенным числом итераций 
	(повторений)

	Для него используется следующий синтаксис:

	FOR <counter> = <initial value> TO/DOWNTO <final value> [step <int> = 1]
	...
	END

	Основные параметры:
	<counter> - переменная, которая используется в качестве счетчика
	итераций (повторений) цикла.

	<initial value> - стартовое значение счетчика

	TO/DOWNTO - при TO счетчик будет наращивать свое значение, при DOWNTO
	уменьшать.

	<final value> - конечное значение цикла, при котором он завершит работу
	Помните, что при DOWNTO конечное значение должно быть меньше стартового

	<step> - значение приращения или уменьшения счетчика при итерациях.
	По умолчанию его значение равно 1.

	Пример цикла:

	...
	var
	 $value: int = 0
	 $final: int = 100
	end

	FOR $MyCounter = 1 to $final step 2
	 $value += $mycounter
	end
	...

..........................................................................

			2.5.2 Оператор WHILE..END
..........................................................................

	Синтаксис:

	WHILE <condition>
	 ...
	END

	Цикл WHILE работает до тех пор, пока выполняется условие. Условие
	проверяется перед итерациями, поэтому если оно будет сразу ложным,
	то цикл не выполнится никогда.

	$var = 10

	while $var > 11
	 inc($var)
	end

	так как условие в цикле ложно, скрипт никогда не придет на команду
	Inc($var)

	Оператор While может принимать в качестве условий логические 
	константы True и False:
	While True .. End - цикл будет выполняться бесконечно, пока вы не 
	прервете его командой Break.
	While False .. End - цикл будет игнорироваться компилятором.
	

	В текущей версии для цикла WHILE доступно только одно условие.
	Вы можете проверять большее кол-во условий внутри тела цикла и 
	использовать команды Break и Continue.
..........................................................................

			2.5.3 Оператор REPEAT..UNTIL
..........................................................................

	Синтаксис:

	REPEAT 
	 ...
	UNTIL <condition>

	Цикл Repeat работает до тех пор пока не выполнится условие после
	команды Until. Условие проверяется после итераций, поэтому
	цикл всегда будет иметь минимум одну итерацию. 


	Оператор Repeat может принимать в качестве условий логические 
	константы True и False:
	Repeat .. Until True - цикл будет иметь только одну итерацию
	Repeat .. Until False - цикл будет выполняться бесконечно, 
	пока вы не прервете его командой Break.


	В текущей версии для цикла REPEAT доступно только одно условие.
	Вы можете проверять большее кол-во условий внутри тела цикла и 
	использовать команды Break и Continue.

..........................................................................

			2.5.4 Continue и Break
..........................................................................

	Иногда вам может потребоваться пропустить текущую итерацию и перейти 
	к следующей, например после проверки условия. Для этого существует
	ключевое слово Continue. Оно может использоваться в качестве параметра.
	Тогда оно обозначает метку, после которой происходит приращение 
	счетчика и переход к следующей итерации. 

	Например:

	if
	 $currentactor.dead
	jf continue // 'continue' это внутренняя метка в начале цикла

	В качестве отдельной команды оно обозначает опкод 0002 (jump), с 
	переходом на следующую итерацию.

	if
	 not $currentactor.dead
	jf @next
	Continue // jump continue
	:next
	
	Кроме этого существует команда Break, которая прерывает цикл. Она может
	использоваться как отдельная команда так и как параметр (jf break)

..........................................................................

		2.6	Дополнительные команды
..........................................................................

	1. INC - эта команда увеличивает значение переменной, переданной
	как первый параметр, на значение второго параметра.
	Второй параметр может не использоваться, тогда вместо него будет
	установлена 1.

	Inc($IntVariable, $Value)
	=
	$IntVariable += $Value

	Inc(1@)
	=
	1@ += 1
..........................................................................

	2. DEC - эта команда уменьшает значение переменной, переданной
	как первый параметр, на значение второго параметра.
	Второй параметр может не использоваться, тогда вместо него будет
	установлена 1.

	Dec($IntVariable, $Value)
	=
	$IntVariable -= $Value

	Dec(1@)
	=
	1@ -= 1
..........................................................................

	3. MUL - эта команда умножает значение переменной, переданной
	как первый параметр, на значение второго параметра.
	Второй параметр может не использоваться, тогда вместо него будет
	установлена 2.
..........................................................................

	4. DIV - эта команда делит значение переменной, переданной
	как первый параметр, на значение второго параметра.
	Второй параметр может не использоваться, тогда вместо него будет
	установлена 2.
..........................................................................

	5. (sys) ALLOC* - эта команда устанавливает адрес памяти для переменной.
	Должна использоваться только для переменных с ТЕКСТОВЫМИ именами.
	Для остальных адрес памяти устанавливается по их имени:
	переменная $40 всегда будет иметь ячейку памяти #40.

	Alloc($MyVar, 40) - переменная $MyVar будет иметь адрес 40.

	см. также 'help\examples\alloc.txt'

	* команды обозначенные словом (sys) не отражаются в коде, а
	являются вспомогательными для компилятора.
..........................................................................

	6. SQR - эта команда вычисляет квадрат значения (вторую степень)
	переменной, переданной в качестве параметра*.
	
	sqr($var) 
	=
	$var *= $var

	* Тип переменной должен быть определен. см. п. 2.3
..........................................................................

	7. RANDOM - эта функция возвращает случайное число в интервале,
	указанном параметрами.

	$rnd = random(1, $high)

	Данную функцию можно использовать как для типа Integer, так и для
	типа Float. Выбор опкода будет зависеть от типа переменной, в
	которую записывается случайное значение.


..........................................................................

	(NEW)
	7. WriteMem - эта команда записывает значение в определенный адрес
	памяти игры (только для San Andreas)

	(!) Данная команда работает только после установки Xieon's SA MemPatch.
	Данный патч и руководство к нему лежат в папке 'Tools\SA Memory Patch'

	Синтаксис:
	WriteMem(Address: Integer; Value: Integer/Float; [Size: Integer = 4]; VirtualProtect: True/False)


	Address - значение адреса в памяти игры, куда будет записано значение.
	В качестве параметра может использоваться целое число или переменная.

	Value - значение, которое будет записано по указанному адресу.
	Может использоваться целое или дробное число, а также переменная.

	Size (необязательный параметр, по умолчанию равен 4) - 
	Число, определяющий размер записи в байтах. Допустимые значения: 1, 2, 4.

	(!) Если вы используете переменную в качестве данного параметра, компилятор
	не сможет определить используемый размер и запишет значение по умолчанию.
	Если вам все же необходимо указать именно переменную, используйте
	низкоуровневый вариант с опкодами (более подробная информация в ридми к патчу)

	VirtualProtect  (необязательный параметр, по умолчанию равен False) - 
	Данный параметр определяет нужно ли защитить область записи командой
	Virtual Protect. Допустимые значения: True, False


	Смотри также 'Help\Examples\WriteMem.txt'
..........................................................................

	(NEW)
	7. ReadMem - эта команда читает значение по определенному адресу
	памяти игры (только для San Andreas)

	(!) Данная команда работает только после установки Xieon's SA MemPatch.
	Данный патч и ридми к нему лежат в папке Tools\SA Memory patch

	Синтаксис:
	ReadMem(Address: Integer; var Result: Variable; [Size: Integer = 4]; VirtualProtect: True/False)


	Address - значение адреса в памяти игры, откуда будет прочитано значение.
	В качестве параметра может использоваться целое число или переменная.

	Result - переменная, в которую будет записан результат

	Size (необязательный параметр, по умолчанию равен 4) - 
	Число, определяющий размер чтения в байтах. Допустимые значения: 1, 2, 4.

	(!) Если вы используете переменную в качестве данного параметра, компилятор
	не сможет определить используемый размер и запишет значение по умолчанию.
	Если вам все же необходимо указать именно переменную, используйте
	низкоуровневый вариант с опкодами (более подробная информация в ридми к патчу)

	VirtualProtect  (необязательный параметр, по умолчанию равен False) - 
	Данный параметр определяет нужно ли защитить область чтения командой
	Virtual Protect. Допустимые значения: True, False

..........................................................................

		2.7	Ключевые слова (кейворды)
..........................................................................

	Заменяют собой опкоды для простых команд. Например кейворд WAIT при 
	компиляции будет заменен на опкод 0001. Т.е. можно писать

	wait 0
 
	вместо 

	0001: wait 0 

	Список кейвордов вызывается нажатием Ctrl+Space

..........................................................................

		2.8	Условия
..........................................................................

	Для проверки условия (-ий) необходимо использовать оператор IF.

	Допускается использование двух видов проверки: 
	1) низкоуровневое
	2) высокоуровневое

	1. Используется следующий синтаксис:

	00d6: if <N>
	... <condition 1>
	... <condition 2>
	...
	... <condition n+1>
	004d: jump_if_false <label>

	<N> - параметр, обозначающий количество условий.
	0 	- проверяется 1 условие
	1..6 	- 2 и более условий (6 макс.), связанных логическим 
	оператором AND. Это значит что проверка выполнится, если ВСЕ условия,
	входящие в нее, верны.
	21..26 	- 2 и более условий (6 макс.), связанных логическим оператором
	OR. Это значит что проверка выполнится, если хотя бы ОДНО условие,
	входящее в нее, верно.

	<label> - имя метки, на которую должен перейти скрипт, если условие
	ложно.

	Sanny Builder допускает не использовать параметр 0 для одиночного
	условия. Таким образом, IF тоже самое что IF 0.

	Также вы можете использовать ключевые слова AND или OR вместо числовых
	параметров*. Тогда компилятор сам будет высчитывать необходимое 
	значение. 

	Например:

	if and 
	 $var > 0
	 $var2 == 10.0
	jf @anywhere

	Компилятор подставит цифру 1 вместо and.

	* В опциях должна быть включена проверка условий.
	IF AND - условия связываются логическим оператором And (1..6)
	IF OR -  условия связываются логическим оператором OR (21..26)


	2. Sanny Builder поддерживает конструкции IF..THEN..END и 
	IF..THEN..ELSE..END*

	Создание условия происходит по правилам, описанным выше.
	После слова THEN вы указываете команду (-ы), которые должны выполняться,
	если условие верно. После слова ELSE вы указываете команду (-ы), 
	которые должны выполняться, если условие ложно. Условие заканчивается
	словом End.

	if $var == 5
	 then 
	  Inc($var)
	 else
	  Dec($var)
	end

	Допускается использование вложенных условий.

	* В опциях должна быть включена проверка условий.


	В качестве операторов сравнения в условиях могут использоваться 
	следующие их виды*:
	
	a == b	 a равно b
	a >= b 	 a больше либо равно b
	a  > b	 a больше b
	a  < b	 a меньше b
	a <= b	 a меньше либо равно b
	a <> b	 a не равно b

	Поддерживаются также их вариации со словом NOT.

	* При условии, что вы не используете опкод в выражении.


..........................................................................

		2.9	HEX..END
..........................................................................

	Данная конструкция предназначена для прямой записи шестнадцатиричных
	значений в SCM или IMG файл*. 
	Например:

	 hex
	  04 00 02 0800 04 01
	 end

	Это будет тоже самое, что 0004: $2 = 1


	(NEW) 
	В качестве значений в данной конструкции можно указывать метки и
	глобальные переменные. Они будут компилироваться как числа, без указания
	типа данных.

	:get_offset
	hex
	 04 00 02 $PLAYER_CHAR 01 @get_offset
	end

	Это будет тоже самое, что 0004: $PLAYER_CHAR = @get_offset


	* Рекомендуется только для опытных скриптеров. Любые ошибки повлекут 
	невозможность последующего декомпилирования файла и чтения его игрой.


..........................................................................


		3. Редактор


..........................................................................


	Sanny Builder как среда программирования предоставляет пользователю
	следующие возможности:

		
		1. Подсветка синтаксиса

	Есть возможность раскрашивать в любые цвета параметры опкодов, 
	комментарии, ключевые слова. Набор ключевых слов содержится в файлах
	keywords.txt и keywords.ini


		2. Быстрый переход по тексту

	Для этого есть два способа: 
	
	1. Установить на нужной строке маркер 
	комбинацией клавиш Ctrl + Shift + <0..9>, а затем быстро перейти 
	к этой строке комбинацией Ctrl + <0..9>. 
	Удалить все маркеры можно через меню Edit -> Clear All Boookmarks
	
	2. Через опцию Go To Line. Она вызывается комбинацией Ctrl+G. 
	Вводите порядковый номер нужной строки, и редактор быстро переместит Вас к ней.


		3. Быстрый переход по меткам

	Для этого установите курсор на какой-либо метке, например @MyLabel. 
	Нажмите Ctrl+Num2 и редактор переместит курсор к строке 
	с этой меткой (:MyLabel). Вернуться обратно можно нажатием Ctrl+Num8.
	Также можно исследовать переходы (jumps). Для этого установите курсор на метку
	(например, @MyLabel) и нажмите Ctrl+Num4 для перехода на строку с другим
	переходом на эту же метку, находящуюся выше. Или Ctrl+Num6 на переход, 
	находящийся ниже. Если больше таких переходов нет, то позиция курсора 
	меняться не будет.


		4. Показ различной информации о текущем опкоде 
		(опция Показывать информацию об опкодах)

	Сейчас реализован вывод количества параметров опкода и, если курсор
	находится над именем модели, цифрового значения модели (только для
	моделей из IDE - файлов и только когда определена директория San Andreas).


		5. Конвертирование исходников из SAMB

	В текущей версии поддерживается формат SAMB 0.33. 
	Для конвертации откройте файл в Sanny Builder и выберите пункт 
	меню Сервис->Конвертация->MB->SB
	(NEW)
	Также можно конвертировать отдельный, выделенный участок кода.

	Внимание: при конвертировании используется файл MB.ini, в котором
	содержатся текстовые имена переменных и значения адресов памяти. 
	Содержимое данного файла критически важно при конвертировании переменных 
	с DMA - функцией (например $MyVar(1) ). Если Вы добавляли свои переменные
	в файл variables.ini в SAMB 0.33, используйте его (переименовав
	в файл MB.ini).


		6. Подбор опкодов. 
	
	Напишите часть опкода (например fade) и нажмите F1.
	Программа из файла opcodes.txt выберет первую строку с этим словом.
	(0169: set_fade_color 0 0 0). Если Вам нужен другой опкод с этим словом,
	нажмите F1 нужное количество раз.
	Вы можете составить свой список опкодов из текущего исходника через опцию
	Сервис->Построить opcodes.txt


		7. Чтение координат и угла разворота игрока (NEW)

	Нажмите Ctrl+Alt+1, когда запущен SA, и появится окно менеджера.
	Здесь вы можете установить новые координаты и угол разворота и 
	скопировать текущие.
	Также вы можете быстро вставить координаты игрока в текст комбинацией 
	Ctrl+Shift+C.
	Вставка угла разворота (z_angle) в текст производится нажатием Ctrl+Shift+E


		8. Поддержка макросов

	Иногда скриптеру необходимо писать одни и те же строки кода, например
	для загрузки моделей. Чтобы сократить время написания такого кода, вы
	можете вызвать специальный макрос, который вставит в редактор нужный
	код. Для этого напишите ключевое слово, соответствующее этому макросу,
	например load и нажмите F2. В редакторе появится код

	#.Load

	while not #.Available
	 wait 0
	end

	Вам останется только написать нужное имя модели в качестве параметра.

	Список используемых макросов содержится в файле 'macroes.txt'. 
	Используется следующий синтаксис:

	Имя макроса (ключевое слово) пишется обычной строкой. 
	На этой же строке можно добавить краткое описание макроса. 
	Для этого достаточно поставить знак = (равно), а после добавить 
	описание. Поддерживаются только	однострочные описания.

	После строки с именем записывается содержимое макроса, 
	каждая строка обозначается символом =.
	Место, куда должен быть помещен курсор после вставки обозначается
	символом |.

	В ходе работы можно вызвать список макросов комбинацией Ctrl+J.

	Также можно добавить свой макрос в файл 'macroes.txt' прямо
	из редактора. Для этого достаточно выделить нужный кусок текста и
	выбрать меню "Сервис->Добавить макрос". В появившемся диалоговом
	окне вы должны ввести имя нового макроса (вместе или без описания)
	и нажать кнопку OK. Новый макрос будет сразу же готов к использованию.

	Также существует возможность создавать свои собственные макросы в ходе работы.
	По сути редактор будет запоминать нажатия любых клавиш и потом вопроизводить
	их в том же порядке.
	Например, у вас есть код:

	$Actor = Actor.Create(CivMale, #MALE01, 100.0, 100.0, 10.0)
	$ActorWithGun = Actor.Create(CivMale, #MALE01, 110.0, 100.0, 20.0)
	$Gang01 = Actor.Create(CivMale, #MALE01, 120.0, 100.0, 30.0)
	$Gang02 = Actor.Create(CivMale, #MALE01, 130.0, 100.0, 40.0)
	$Killer = Actor.Create(CivMale, #MALE01, 140.0, 100.0, 50.0)
	$ActorWithoutGun = Actor.Create(CivMale, #MALE01, 150.0, 100.0, 60.0)

	Допустим, Вам нужно обменять имена актеров в кажой паре (поставить вместо
	$Actor $ActorWithGun, а вместо $ActorWithGun - $Actor и т.д.)
	Путем записи макроса можно сократить время написания такого кода.
	(кто работал в Дельфи, тот поймет :)).

	Поставьте курсор на первую строку и нажмите Ctrl+M. С этого 
	момента редактор запоминает все нажатия клавиш, так что будьте осторожны.
	-Зажмите Ctrl и нажмите один раз стрелку вправо. Ctrl нужен так как
	строки разной длины. 
	-Теперь нажмите Shift+Home и Ctrl+Ins. 
	-Нажмите стрелку вниз. Вы должны оказаться на второй строке, при этом 
	глобальная переменная будет в буфере обмена. 
	-Нажмите Ctrl+стрелка вправо и Shift+Ins.
	-Нажмите Ctrl+стрелка влево, Shift+Home, Ctrl+Ins и кнопку Delete
	-Нажмите стрелку вверх
	-Нажмите Ctrl+Shift+стрелка вправо и Shift+Ins
	-Нажмите кнопку Home.
	
	Теперь первые две строки выглядят как
	$ActorWithGun = Actor.Create(CivMale, 100.0, 100.0, 10.0)
	$Actor = Actor.Create(CivMale, 110.0, 100.0, 20.0)
	и курсор стоит в начале первой строки. Теперь нажмите Ctrl+M

	Макрос записан. Теперь вы можете воспроизводить нажатия клавиш 
	комбинацией Ctrl+P. Установите курсор на 3-ю строку, нажмите
	Ctrl+P и имена актеров поменяются местами.

	Во время записи макроса можно включить паузу нажатием Ctrl+P.
	Продолжить запись - Ctrl+P.


		9. Замена номеров миссий на их имена.

	Sanny Builder допускает использовать вместо номера миссии ее имя.
	Именем миссии явялется имя ее метки, которая определена в блоке
	DEFINE MISSION.

	Например, если у вас есть

	DEFINE MISSION 10 AT @MYMISSION

	то вы можете использовать вместо 

	start_mission 10

	команду

	start_mission MYMISSION

	В SB добавлена опция Replace Mission Numbers. Когда она включена,
	декомпилятор автоматически заменяет все номера миссий в коде на их имена.
	На компилятор эта опция не влияет, он поддерживает оба варианта.

	Эта опция дает возможность безболезненно удалять миссии, не
	заботясь о переименовывании всех последующих номеров в коде. 
	Все что нужно, это изменить блок DEFINE MISSION. 

	Для дополнительного удобства в строке start_mission можно
	вызвать список имен миссий и их номеров нажатием Ctrl+Space.

	Также можно быстро перейти с имени миссии на нее саму. Переход
	осуществляется так же, как и переход на метку (пункт 3.3)


		10. Многоязычный интерфейс.

	Начиная с версии 2.98 Sanny Builder поддерживает различные варианты
	перевода интерфейса и сообщений. В стандартной комплектации доступны
	русскоязычный и англоязычный варианты. Переключить язык можно через
	опции (F10).
	Информация по созданию своего перевода содержится в файле 
	'lang\How to translate.txt'


		11. Различные режимы редактирования

	Sanny Builder может редактировать скрипты игр GTA3, GTA VC, GTA SA.
	Текущий режим отображается в нижнем правом углу программы.
	(NEW)
	Переключить режимы редактирования можно через контекстное меню, 
	которое появляется при клике по названию текущего режима.


		12. Меню внешних приложений.

	Вы можете добавить в меню Инструменты до 9 внешних приложений, 
	которые будут запускаться когда они вам понадобятся. Каждому
	приложению можно присвоить комбинацию горячих клавиш и ряд
	параметров, необходимых для запуска.
	(NEW)
	В качестве параметра запускаемого приложения может использоваться
	специальное слово: $SB_FileName. Оно обозначает имя текущего 
	открытого файла и может быть передано во внешнее приложение.


		13. Комментирование кода

	Коментарии обозначаются в коде двойным слешем //
	Все, что идет после данного знака до конца строки, игнорируется компилятором.

	Для того чтобы закомментировать несколько строк сразу либо только часть 
	строки (например в середине или начале) вы можете использовать блочные комментарии {}

	0001: wait  {это игнорируется} 0 ms


	Также вы можете закомментировать несколько строк выделив их и нажав 
	Ctrl+Q
	Для раскоментирования выделите текст и нажмите Ctrl+Q еще раз.


		14. Собственные имена для меток (NEW).

	Вы можете давать меткам собственные имена, которые не будут зависеть
	от опций декомпилятора. Перечень имен содержится в файле CustomLabels.ini
	(отдельный для каждой игры). 
	Формат записи следующий: <label address>=<custom name> 
	Если декомпилятор встретит метку по данному адресу, он заменит ее на
	указанное имя.


	Узнать адрес метки можно включив в опциях формат меток "Смещение от начала". 
	После декомпиляции файла, число после слова Label и будет адресом метки.


		15. Консоль Sanny Builder (NEW)

	Консоль может использоваться для включения/отключения отдельных
	опций программы, недоступных иным способом. Большинство из них
	явялются опциями (де)компилятора.
	Вызвать консоль можно нажатием Ctrl + ~.

	Консоль принимает текстовые команды из поля ввода.
	Более подробную информацию вы можете получить, набрав в консоли слово HELP.

..........................................................................

	Кроме этого помимо стандартных работают следующие комбинации клавиш:

	Ctrl + Alt + U/I - двигать выделенный блок влево/вправо (таб)
	Ctrl + Alt + A/D - двигать выделенный блок влево/вправо (символ)

	Ctrl + Alt + B/N/M - различные режимы выделения текста:
	Обычный, По столбцам (аналог - выделение с зажатым Alt), По строкам

	Ctrl + Shift + B - переход между фигурными скобками {}
	Ctrl + Shift + Num8/Num2 - прокрутить страницу на одну строку вверх/вниз
	Ctrl + Scroll Up/Down - страница вверх/вниз

	Ctrl + Shift + U/L - перевод слова в верхний/нижний регистр

	Ctrl + T - удалить слово
	Ctrl + Y - удалить строку
	Ctrl + Shift + Y - очистить строку

	Ctrl + Space - показать список классов/свойств/моделей/меток/переменных/миссий
	Ctrl + Shift + Space - показать подсказку для текущей команды класса

	Ctrl + Shift + C - вставить текущие координаты игрока (3.7)
	Ctrl + Shift + E - вставить текущий угол поворота игрока (3.7)

	Alt + S (когда активен список моделей) - пересортировать список

	F1 - искать опкод с данным словом (без учета '_' и '.')
	Ctrl + F1 - искать опкод с данным словом (с учетом '_' и '.')

	F2 - использовать макрос
	Ctrl + J - вызвать список макросов
	Ctrl + M - запись последовательности нажатия клавиш/остановка записи
	Ctrl + P - воспроизведение записанной последовательности/пауза во время записи

	Ctrl + ` - вызвать консоль

..........................................................................


		4. Поиск опкодов (Opcode Search Tool)


..........................................................................


     Вы можете вызвать программу OST нажатием Ctrl+Alt+2 или через меню
     Сервис->Инструменты->Поиск опкодов

    
     Чтобы найти нужный опкод, впишите в верхнем поле слова, 
     соответствующие ему, например 'actor car' (без кавычек). В списке
     останутся команды, содержащие эти слова. Вписывайте уточняющие
     слова, пока нужный опкод не будет найден. При поиске можно 
     пользоваться специальными операторами (подробнее о них ниже).
    
     Также программа учитывает кол-во введенных одинаковых слов и ищет
     их в необходимом количестве. Т.е, если вы напишете три слова 'car',
     то программа будет искать опкоды, в которых именно три слова car.
    
     Вы можете регулировать задержку перед началом поиска. Если вы 
     хотите найти длинное слово, например 'weapon', то лишний отсев, 
     который происходит, пока вы пишете слово, может быть нежелателен. 
     Чтобы увеличить или уменьшить задержку, откройте настроечный файл 
     settings.ini и измените значение параметра delay на нужное. 
     Единица измерения - миллисекунда. По умолчанию задержка - 300 мс.
    
     Есть также еще один вариант. Измените значение параметра 
     extra_search на 1, и теперь, если SCROLL LOCK будет включен, то
     поиск осуществляться не будет. Напишите нужное вам выражение,
     отключите SCROLL LOCK, и поиск будет осуществлен.
    
    
    	Копирование:
    	------------
    
     После того, как вы нашли нужный вам опкод, выделите его в списке
     и нажмите ENTER. Опкод будет записан в буфер. Если вы хотите 
     добавить к нему еще один опкод, нажмите SHIFT+ENTER. Тогда в 
     буфере обмена будет уже два ваших опкода.
     F2 - скопировать весь список целиком.
    
    
    	Горячие клавиши:
	----------------
  
   
     ESC, F12 - выход
   
     ENTER 
     * по выденному опкоду - скопировать в буфер
    
     SHIFT + ENTER  
     * по выденному опкоду - добавить его к содержимому буфера
    
     SCROLL LOCK (при параметре extra_search=1) включить/отключить поиск
    
     F2 - скопировать все опкоды в списке в буфер
    
     F3 - сортировка по опкодам
     F4 - сортировка по словам
    
     F5 - встать в форму поиска
     F6 - встать в список опкодов
    
     F11 - очистить строку поиска, показать все опкоды
    
    
   
    	Операторы поиска:
 	-----------------   
       
    
    		ЛОГИЧЕСКИЕ ОПЕРАТОРЫ
    
    
     ---------------------------------------------------------------
    
    	Оператор И (AND)
    
     ---------------------------------------------------------------
    
     В программе эту функцию выполняет одиночный пробел между словами. 
    
    		Пример: @ player
    
     Будут показаны опкоды, где встречаются И символ @, И слово player
    
    
     ---------------------------------------------------------------
    
    	Оператор ИЛИ (OR)
    
     ---------------------------------------------------------------
    
     В программе эту функцию выполняет символ | между словами. 
    
    		Пример: @ | player
    
     Будут показаны опкоды, где встречаются ИЛИ символ @, ИЛИ слово player
    
     Если поставить | первым элементом, программа будет связывать все
     последующие слова оператором OR.
    
    		Пример: | actor player car
    
     Будут показаны опкоды, где есть хотя бы одно из этих слов.
    
     ---------------------------------------------------------------
    
    	Оператор НЕТ (NOT)
    
     ---------------------------------------------------------------
    
     Для всех случаев это два минуса перед исключаемым словом --
    
    		Пример: car --car2
    
     Будут показаны опкоды, где ЕСТЬ слово car И НЕТ слова car2
    
     Для слов и символов $ и @ можно использовать один минус. Это
     сделано, чтобы не перепутать исключение с поиском отрицательных 
     чисел.
    
    		Пример: -10 -@ -car --3
    
     Будут показаны опкоды, где ЕСТЬ число -10 И НЕТ символа @, 
     слова car и цифры 3.
    
    
     ---------------------------------------------------------------
    
    		ДРУГИЕ ОПЕРАТОРЫ 
    
     ---------------------------------------------------------------
    
    	^ :: показать все условия в списке
    
     --------------------------------------------------------------
    
    	^выражение :: найти выражение в условных опкодах
    
    		Пример: ^car ==
    
     Будут показаны условные опкоды, где есть слово car и знак ==
    
     ---------------------------------------------------------------
    
    	-^  :: исключить все условия из списка
    
    		Пример: player -^
    
     Будут показаны все опкоды, где есть слово player, и этот опкод 
     не является условием в IF.
    
     ----------------------------------------------------------------
    
    	-^выражение :: исключить условия, содержащие выражение 
    
    		Пример: player -^actor
    
     Будут показаны все опкоды, где есть слово player, исключая 
     условные опкоды со словом actor.
    
     ----------------------------------------------------------------
    
    	% :: искать в заданном порядке
    
    		Пример: % @ == @
    
     Будут показаны все опкоды, где эти символы идут в данном порядке
    


..........................................................................


		5. История изменений


..........................................................................


		Текущая версия:

	* добавлены две новые команды WriteMem и ReadMem (2.6)
	* поддержка чисел в шестнадцатиричном формате (2.2)
	* конструкция hex..end может принимать значения меток и глобальных переменных (2.9)
	* поддержка типа данных & для массивов, а также в выражениях без
	  опкодов: &57 += &120(&231,4i)
	* возможность давать собственные имена меткам (3.14)
	* возможность выбирать регистр букв для собственных имен меток и 
	  переменных, а также стринговых переменных (Настройки -> Форматирование)
	* добавлена консоль для специальных опций SB (3.15)
	* поддержка GXT-файлов GTA III, GTA VC
	* поддержка символьных констант в длинных стрингах (2.2)
	* минорные исправления и добавления
	  - информация об авторе и версии INI файла
	  - поддержка классами INI с оригинальным порядком следования параметров 
	    (как SASCM.INI от PLPython)
	  - опция подтверждения выхода
	  - возможность быстро переключать режим редактирования (3.11)
	  - конвертация отдельного, выделенного участка кода SAMB 0.33
	  - возможность передавать во внешнее приложение в качестве параметра 
	    имя текущего открытого файла (3.12)
	  - исправлены некоторые ошибки в конфигурационных файлах
	  - убрана автоматическая конвертация числа в тип Float, если переменная
	    была объявлена как Float, а в нее записывалось целое число. Теперь
	    опкод выбирается только в зависимости от типа числа.
	  - чтение/изменение Z_angle игрока в Coord Manager; возможность вставки
	    значения угла в скрипт нажатием Ctrl+Shift+E (для SA)

	(!) В SASCM.INI изменены три опкода: 0181, 00c3, 00c4 для поддержки
	команд WriteMem и ReadMem. В оригинальных файлах данные опкоды не 
	встречаются и игрой не поддерживаются, так что проблем с работой не должно
	быть. Опкоды добавлены для более быстрой установки Xieon's SA MemPatch (2.6)

	(!) в файле classes.db для SA член класса Car.SetSpeedInstantly был
	поименован неверно (перепутан опкод). Если при компиляции вы 
	встретите сообщение об ошибке с этим методом, переименуйте его в 
	Actor.DrivingPlane вручную. Приносим свои извинения.


		Предыдущие релизы:

	04.08.2006	release #13	v. 2.98

	* Sanny Builder полностью русифицирован
	* добавлено меню внешних приложений
	* в SB встроена специальная версия Opcode Search Tool 
	  (http://gtacoding.nm.ru/tool). Подробности в файле 'Readme OST.txt'
	* проверка математических выражений при декомпиляции 
	  с выключенной опцией "Писать опкоды"*
	* возможность выбирать IMG-файл самостоятельно, если таковой не найден 
	  в папке с SCM-файлом (опция "Ручной выбор IMG-файла")
	* возможность добавлять новые макросы прямо из редактора;
	  добавлены описания макросов
	* список моделей можно сортировать по алфавиту/по значению 
	  (Alt+S, когда активен список)
	* минорные исправления и изменения


	Прим. * Если при компиляции опкод был использован неправильно 
	(например 0004: $Var1 = $Var2), то декомпилятор запишет строку вместе 
	с опкодом и добавит в исходник комментарий об этом.


	11.06.2006	release #12	v. 2.97

	* новый тип данных: & (direct byte address)
	* минорные изменения


	Полный список всех релизов:
	http://sannybuilder.com/views/history



..........................................................................


		6. Дополнительная информация


..........................................................................

	Программа написана на Delphi 7.0 Ent.	Borland Software Corp.
						http://www.borland.com

	Был использован компонент SynEdit	SynEdit Team
						http://synedit.sourceforge.net

	С замечаниями, советами и предложениями обращаться на 
	mail@sannybuilder.com


	Web:
	http://sannybuilder.com
	http://gtaforums.com/index.php?showtopic=211077




	Use it at your own risk. In Backup We Trust.
				Best regards, Seemann and Xieon

..........................................................................
