(YASL53DP) 3D-проекты Silverlight 5 с наддувом на Babylon Toolkit

Грег Дункан

(Еще одно сообщение по Silverlight 5 3D)

Я знаю, что уже недавно писал о Silverlight 5 и движке/инструментарии. Это должно быть ненадолго, по крайней мере, для материалов по Silverlight 3D. Но это сообщение на некоторое время прожгло дыру в моей записной книжке OneNote, в которой я планирую сообщения для блога C4F, так что…

Ответ: Обеспечивает полный инструментарий для Silverlight 5 3D

И включает:

  • Завершенный класс Effect с шейдерами и поддержкой параметров (с интегрированными шейдерами и системой кеширования регистров)
  • Модель объектов Model/ModelMesh/ModelMeshPart
  • Модель объектов ModelContent/ModelMeshContent/ModelMeshPartContent для создания иерархии моделей
  • Систему импортирования с поддержкой .OBJ-файлов
  • Классы камер:
    • Орбитальная камера
    • Нормальная камера
  • BasicEffect для простых режимов рендеринга с поддержкой:
    • Рассеянных цветов и текстур
    • Отраженных цветов и текстур
    • Выпуклых текстур
    • Окружающих цветов
    • Точечных источников света
  • Система пересечений лучей
    • BoundingSphere (Окаймляющая сфера)
    • Каркас против луча

Вопрос: Что такое Babylon Toolkit

Любой с моделью Viper получает дополнительный зачет...

clip_image002

Инструментарий и пример идут в смешанной форме с двоичным и исходным кодом на странице выпуска v1.0.3. Если вы скачиваете исходники примера Babylon.Toolkit.Sample.zip, также скачайте двоичные файлы библиотеки Babylon.Toolkit. Затем после открытия проекта примера, исправьте ссылки, используя библиотеки DLL из двоичной загрузки.

clip_image004

Теперь если вы получите полный исходник для проекта и захотите самостоятельно его скомпилировать, вначале прочитайте сообщение «Все мы – один маленький мир… как показано на 3D-примере Silverlight 5, Solar Wind», рассказывающее о том, что надо сделать, чтобы их откомпилировать. Оба используют Shader MSBuild Task… ИЛИ если у вас уже установлен DirectX SDK, вы заходите в каталог Libs и запускаете ShaderBuildTaskSetup.msi чтобы установить MSBuild Task.

clip_image006

Так что в любом случае...

Как же на самом деле выглядит Viper?

clip_image008clip_image010

(В конце концов я не вижу кода…Здесь блондины, рыжие…)

Отобразить Viper на экране достаточно просто.

Вот главный цикл прорисовки:

 private void DrawingSurface_Draw(object sender, DrawEventArgs e)
 {
     if (model == null)
     {
         Dispatcher.BeginInvoke(() => InitModel(e.GraphicsDevice));

         statesManager = new StatesManager(e.GraphicsDevice);
     }

     if (model == null)
         return;

     DateTime start = DateTime.Now;

     // States
 statesManager.DepthBufferEnable = true;
     statesManager.CullMode = CullMode.None;
     statesManager.ApplyDepthStencilState();
     statesManager.ApplyRasterizerState();
     e.GraphicsDevice.BlendState = BlendState.AlphaBlend;

     // Draw
 e.GraphicsDevice.Clear(ClearOptions.Target | ClearOptions.DepthBuffer, new Color(0, 0, 0, 0), 1.0f, 0);

     foreach (ModelMesh mesh in model.Meshes)
     {
         foreach (BasicEffect basicEffect in mesh.Effects)
         {
             basicEffect.SceneAmbientColor = new Color(0.3f, 0.3f, 0.3f, 0);
             basicEffect.World = Matrix.Identity;
             basicEffect.View = camera.View;
             basicEffect.Projection = camera.Projection;
             basicEffect.LightPosition = camera.Position + new Vector3(1, 5, 3);
             basicEffect.CameraPosition = camera.Position;

             basicEffect.EmissiveColor = mesh == selectedMesh ? new Color(0.5f, 0.5f, 0.5f, 0) : Color.Black;
         }
     }

     model.Draw();

     camera.ApplyInertia();

     double duration = (double)DateTime.Now.Subtract(start).Ticks / TimeSpan.TicksPerMillisecond;
     int verticesCount = model.Meshes.Sum(v => v.VerticesCount);
     Dispatcher.BeginInvoke(() =>
                                {
                                    frameTime.Text = string.Format("Frame time : {0:0.00} ms / {1:0.00} fps", duration, 1000 / duration);
                                    counters.Text = string.Format("Vertices count : {0}", verticesCount);
                                });

     e.InvalidateSurface();
 }

Какие вызовы InitModel фактически загружают Viper:

 private void InitModel(GraphicsDevice device)
{
    Stream objStream = Application.GetResourceStream(new Uri("/Babylon.Toolbox.Sample;component/Models/Viper-mk-IV-fighter.obj", UriKind.Relative)).Stream;
    ObjImporter importer = new ObjImporter();

    importer.OnImportCompleted += m =>
    {
        waitBar.Visibility = Visibility.Collapsed;
        model = m.BuildModel(device, new ModelBuilding.BasicEffectMaterialConverter());

        camera.Radius = model.BoundingSphere.Radius * 1.5f;
        camera.Target = model.BoundingSphere.Center;

        drawingSurface.Invalidate();
    };

    // Report loading progress
 importer.OnImportProgressChanged += p =>
    {
        waitProgressBar.Value = p;
    };

    waitBar.Visibility = Visibility.Visible;

    importer.ImportAsync(objStream, GetResourceStream, ImportationOptions.Optimize | ImportationOptions.GeneratePickingInformations);
}

После загрузки обводим камеру вокруг:

 private void drawingSurface_MouseMove(object sender, System.Windows.Input.MouseEventArgs e)
 {
     Point currentPosition = e.GetPosition(drawingSurface);

     switch (currentMode)
     {
         case MouseMode.ArcRotate:
             if (!mouseLeftDown)
                 return;

             camera.InertialAlpha += (float)(currentPosition.X - startPosition.X) * camera.AngularSpeed;
             camera.InertialBeta -= (float)(currentPosition.Y - startPosition.Y) * camera.AngularSpeed;
             startPosition = currentPosition;
             break;
         case MouseMode.ObjectPicking:...

Так что если вы занимаетесь трехмерным моделированием в Silverlight 5 – не изобретайте колеса. Есть ряд замечательных наборов инструментов и движков, подобных Babylon Toolkit. Помните, друзья не позволяют друзьям тратить ненужные усилия над тем, что свободно доступно везде... clip_image012

Несколько ссылок, которые могут быть интересны: