VRML в примерах
Язык VRML (Virtual Realty Modelling Languagy) предназначен для описания трехмерных изображений и оперирует объектами, описывающими геометрические фигуры и их расположение в пространстве. Vrml-файл представляет собой обычный текстовый файл, интерпретируемый браузером. Поскольку большинство браузеров не имеет встроенных средств поддержки vrml, для просмотра Vrml-документов необходимо подключить вспомогательную программу - Vrml-браузер, например, Live3D или Cosmo Player. Как и в случае с HTML, один и тот же vrml-документ может выглядеть по-разному в разных VRML-браузерах. Кроме того, многие разработчики VRML-браузеров добавляют нестандартные расширения VRML в свой браузер. Существует немало VRML-редакторов, делающих удобней и быстрее процесс создания Vrml-документов, однако несложные модели, рассматриваемые в данной статье, можно создать при помощи самого простого текстового редактора. Единицы измерения В VRML приняты следующие единицы измерения:
Как уже говорилось, Vrml-документ представляет собой обычный тестовый файл. Для того, чтобы VRML-браузер распознал файл с VRML-кодом, в начале файла ставится специальный заголовок - file header: #VRML V1.0 ascii Такой заголовок обязательно должен находиться в первой строке файла, кроме того, перед знаком диеза не должно быть пробелов. Примитивы VRML В VRML определены четыре базовые фигуры: куб (верней не куб, а прямоугольный параллепипед), сфера, цилиндр и конус. Эти фигуры называются примитивами (primitives). Набор примитивов невелик, однако комбинируя их, можно строить достаточно сложные трехмерные изображения. Например, вот такие: Рассмотрим поподробней каждый из примитивов.
Куб Возможные параметры: width - ширина, height - высота, depth - глубина. Cube { width 2 # ширина height 3 # высота depth 1 # глубина } Параметр у сферы только один, это radius. Sphere { radius 1 # радиус } Возможные параметры: bottomRadius - радиус основания, height - высота, parts - определяет, какие части конуса будут видны. Параметр parts может принимать значения ALL, SIDES или BOTTOM. Cone { parts ALL #видны и основание, и боковая поверхность конуса bottomRadius 1 #радиус основания height 2 #высота } Для цилиндра можно задать параметры radius и height. Кроме того, с помощью параметра parts для цилиндра можно определить будут ли отображаться основания цилиндра и его боковая поверхность. Параметр parts может принимать значения ALL, SIDES, BOTTOM или TOP. Cylinder { parts ALL #видны все части цилиндра radius 1 #радиус основания height 2 #высота цилиндра } Цвет фигуры, определяется с помощью объекта Material. Material { ambientColor 0.2 0.2 0.2 diffuseColor 0.8 0.8 0.8 specularColor 0 0 0 emissiveColor 0 0 0 transparency 0 } Параметры ambientColor, diffuseColor, specularColor и emissiveColor управляют цветами и указываются в палитре RGB (красный, зеленый и голубой), причем первая цифра определяет интенсивность красного цвета, вторая - зеленого, а третья - синего. К примеру, синий кубик, может быть описан следующим образом: #VRML V1.0 ascii Material { diffuseColor 0 0 1 } Cube {} Параметр transparency может принимать значения от 0 до1 и определяет степень прозрачности, причем максимальная прозрачность достигается при transparency равном единице. В приведенном примере описано два цилиндра разных размеров, меньший из которых просвечивает сквозь другой. #VRML V1.0 ascii Material { diffuseColor 0 0 1 transparency 0.7 } Cylinder { height 1 radius 1 } Material { emissiveColor 1 0 0 transparency 0 } Cylinder { height 0.8 radius 0.1 } Для имитирования различных поверхностей в VRML существует объект Texture2. В качестве текстуры легче всего использовать обычный графический файл, например, в GIF-формате. В таком случае для "натягивания" текстуры на трехмерное изображение нужно только указать путь к файлу в параметре filename объекта Texture2. . #VRML V1.0 ascii Texture2 { filename "krp.gif" image 0 0 0 wrapS REPEAT wrapT REPEAT } Cube { width 1 height 1 depth 1 } Параметры wrapS и wrapT могут принимать значения REPEAT или CLAMP, и управляют натягиванием текстуры по соответственно горизонтальной и вертикальной осям. Положение объектов в пространствеИзменение координат По умолчанию любой описанный нами объект будет располагаться точно по центру окна браузера. По этой причине, если мы опишем к примеру два одинаковых цилиндра, они сольются друг с другом. Для того, чтобы изменить положение второго цилиндра, применим узел Translation. Узел Translation определяет координаты объекта: Translation { translation 1 2 3 #т.е. соответственно x=1 y=2 z=3 } Вообще говоря, координаты указываемые в Translation не являются абсолютными. Фактически это координаты относительно предыдущего узла Translation. Чтобы прояснить это вопрос, рассмотрим пример: #VRML V1.0 ascii Cube { width 1 height 1 depth 1 } # Этот куб по умолчанию располагается в центре Translation { translation 2 0 0 } #Второй куб сдвинут вправо на 2 Cube { width 1 height 1 depth 1 } Translation { translation 2 0 0 } #Третий куб сдвинут вправо на два относительно 2-го !!!! Cube { width 1 height 1 depth 1 } Как видите, третий кубик вовсе не совпадает с первым, хотя в в узле Translation указаны те же координаты. В VRML 1.0 принято следующее правило: узлы, модифицирующие свойства фигур (Translation, Material и т.п.), действуют на все далее описанные фигуры. Чтобы ограничить область действия модифицирующих узлов, фигуры необходимо сгруппировать с помощью узла Separator. Separator { другие узлы } Узел Separator работает как контейнер, он может содержать любые другие узлы, и основным его предназначением является именно ограничение области действия узлов типа Translation и Material. Сравните следующий пример с предыдущим: #VRML V1.0 ascii Separator { Cube { width 1 height 1 depth 1 } }# конец области действия узла Separator Separator { Translation { translation 2 0 0 } #Второй куб сдвинут вправо на 2 Cube { width 1 height 1 depth 1 } }# конец области действия узла Separator Separator { Translation { translation 2 0 0 } #Третий куб сдвинут вправо на два относительно 1-го. Cube { width 1 height 1 depth 1 } }# конец области действия узла Separator Хотя в примере описано три кубика, мы видим только два, так как второй и третий совпадают. Вообще говоря рекомендуется всегда и везде использовать узел Separator. Он не
только избавит от ошибок, связанных с относительностью координат, но и сделает
VRML-код более простым и понятным.
Вращение Для вращения фигур вокруг осей координат применяется узел Rotation. Rotation { rotation 0 1 0 1.57 } Первые три цифры определяет будет ли осуществлен поворот вокруг соответственно осей x, y и z, а четвертая задает угол вращения в радианах. В приведенном выше листинге поворот осуществляется вокруг оси y на 90 градусов.
Составим букву T из двух цилиндров. По умолчанию цилиндр ориентирован вертикально (см. рисунок). Поэтому для успешного выполнения задачи повернем его вокруг оси z на 90 градусов. #VRML V1.0 ascii Separator { #Красный цилиндр Material { emissiveColor 1 0.6 0.6 } Cylinder { height 1 radius 0.3 } } Separator { # Синий цилиндр, повернутый на 90 градусов вокруг оси z Translation { translation 0 0.5 0 } Rotation { rotation 0 0 1 1.57 } Material { emissiveColor 0.5 0.5 1 } Cylinder { height 1 radius 0.3 } } Узел Scale масштабирует фигуры по одному или нескольким измерениям. Три цифры, стоящие после параметра scaleFactor определяют коэффициенты масштабирования относительно осей x,y и z. Scale { scaleFactor 1 1 1 } В следующем примере, узел Scale сжимает сферу по оси x, и из сферы получается эллипсоид. #VRML V1.0 ascii Material { emissiveColor 1 1 0 } Scale { scaleFactor 0.7 1 1 #сжимаем сферу по оси x } Sphere { radius 1} }Определение собственных объектов VRML предоставляет прекрасную возможность сократить и сделать более понятным исходный код VRML-файла путем описания собственных объектов. Это значит, что если в изображении несколько раз повторяется одна и та же фигура, то ее можно описать всего лишь один раз и в дальнейшем только ссылаться на нее. Объект описывается одним из способов: DEF name Cube {} или DEF name Material {} или DEF name Separator { Сгруппированные узлы, описывающие фигуру и свойства материала } Для того, чтобы вставить в VRML-файл ранее определенную фигуру, используется команда USE Separator { USE name } Создадим VRML-файл, описывающий стул, при этом ножку стула опишем как объект LEG: #VRML V1.0 ascii Material { emissiveColor 1 0.5 0.5 } Separator { Translation { translation 1 1 1 } DEF LEG #Определяем объект - ножку стула Separator { # leg Cylinder { height 0.8 radius 0.1 } } # определили ножку } Separator { Translation { translation 0 1 1 } USE LEG # используем определенный объект } Separator { # еще одна ножка Translation { translation 1 1 0 } USE LEG } Separator { # последняя ножка Translation { translation 0 1 0 } USE LEG } Separator { # сиденье Translation { translation 0.49 1.5 0.5 } Cube { height 0.2 width 1.2 depth 1.2 } } Separator { # спинка Translation { translation 0.49 2 0 } Cube { height 0.8 width 1.2 depth 0.2 } } Separator { # закругление спинки Translation { translation 0.49 2.1 0 } Rotation { rotation 1 0 0 1.57 } Cylinder { radius 0.6 height 0.2 } } Как видите, нам не понадобилось описывать каждую ножку в отдельности - в результате объем VRML-кода стал меньше, а сам код более читабельным. Еще один способ уменьшить размер VRML-файла - вставлять фигуры из другого файла. Это позволяет делать узел WWWInline: #VRML V1.0 ascii Separator { WWWInline { name "" bboxSize 0 0 0 bboxCenter 0 0 0 } } Параметр name - это путь к файлу, параметры bboxSize и bboxCenter не обязательны и показывают пользователю размеры и положение вставляемого объекта, пока объект подгружается. Вместо заключения, хочется обратить Ваше внимание на две особенности VRML, незнание которых сильно затруднит создание VRML-документов вручную.
Поделитесь этой записью или добавьте в закладки | Полезные публикации |