Created
April 4, 2012 16:43
-
-
Save mfakane/2303707 to your computer and use it in GitHub Desktop.
XNA と MMDX をコンソールウィンドウで。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
* コンソールウィンドウで XNA をドライヴする | |
* MMDX を動かしてコンソールウィンドウ上に描画、または画像ファイルに出力 | |
* ・XNA Windows Game を新規作成して、Game1.cs を消して、Program.cs にこれを突っ込む | |
* ・コンテントプロジェクトに任意のモデルと任意のモーションを追加 (既定ではモデルは Miku、モーションは TrueMyHeart となっているものを使用する) | |
*/ | |
// tmp/ フォルダを作ってそこに png を出力する | |
// undef するとコンソールウィンドウ上に描画するだけ | |
#define RENDER_TO_FILE | |
using System; | |
#if RENDER_TO_FILE | |
using System.IO; | |
using System.Reflection; | |
#endif | |
using System.Runtime.InteropServices; | |
using System.Threading; | |
using Microsoft.Xna.Framework; | |
using Microsoft.Xna.Framework.Content; | |
using Microsoft.Xna.Framework.Graphics; | |
using MikuMikuDance.Core.Motion; | |
using MikuMikuDance.XNA; | |
namespace MikuMikuConsole | |
{ | |
static class Program | |
{ | |
[DllImport("user32")] | |
static extern IntPtr FindWindow(string lpClassName, string lpWindowName); | |
/// <summary> | |
/// アプリケーションのメイン エントリー ポイントです。 | |
/// </summary> | |
static void Main(string[] args) | |
{ | |
var t = Console.Title; | |
Console.Title = Guid.NewGuid().ToString(); | |
Thread.Sleep(5); | |
var handle = FindWindow(null, Console.Title); | |
Console.Title = t; | |
var services = new GameServiceContainer(); | |
var pp = new PresentationParameters | |
{ | |
BackBufferFormat = SurfaceFormat.Color, | |
BackBufferWidth = 640, | |
BackBufferHeight = 480, | |
DepthStencilFormat = DepthFormat.Depth24, | |
PresentationInterval = PresentInterval.Immediate, | |
IsFullScreen = false, | |
MultiSampleCount = 0, | |
RenderTargetUsage = RenderTargetUsage.DiscardContents, | |
DeviceWindowHandle = handle, | |
}; | |
#if RENDER_TO_FILE | |
var path = Path.Combine(Path.GetDirectoryName(new Uri(Assembly.GetExecutingAssembly().CodeBase).AbsolutePath), "tmp"); | |
if (!Directory.Exists(path)) | |
Directory.CreateDirectory(path); | |
#endif | |
using (var content = new ContentManager(services, "Content")) | |
using (var g = new GraphicsDevice(GraphicsAdapter.DefaultAdapter, GraphicsProfile.HiDef, pp)) | |
{ | |
var gds = new GraphicsDeviceService(g); | |
services.AddService(typeof(IGraphicsDeviceService), gds); | |
services.AddService(typeof(IGraphicsDeviceManager), gds); | |
using (var mmdx = MMDXCore.Instance) | |
using (var model = mmdx.LoadModel("Miku", content)) | |
{ | |
var motion = mmdx.LoadMotion("TrueMyHeart", content); | |
var track = new MMDMotionTrack(motion, MMDMotionTrackOptions.UpdateWhenStopped); | |
const string key = "TrueMyHeart"; | |
model.AnimationPlayer.AddMotion(key, track); | |
model.PhysicsManager.Reset(); | |
track.Start(); | |
for (var i = 0; i < track.MaxFrame; i++) | |
{ | |
Console.Write("\rrendering {0} of {1}..." + new string(' ', 10), i, track.MaxFrame); | |
mmdx.Update(1 / 30f); | |
#if RENDER_TO_FILE | |
using (var rt = new RenderTarget2D | |
( | |
g, | |
pp.BackBufferWidth, | |
pp.BackBufferHeight, | |
false, | |
pp.BackBufferFormat, | |
pp.DepthStencilFormat, | |
pp.MultiSampleCount, | |
pp.RenderTargetUsage | |
)) | |
{ | |
g.SetRenderTarget(rt); | |
g.RasterizerState = RasterizerState.CullCounterClockwise; | |
g.DepthStencilState = DepthStencilState.DepthRead; | |
g.BlendState = BlendState.AlphaBlend; | |
g.Clear(Color.Transparent); | |
model.Draw(); | |
g.SetRenderTarget(null); | |
using (var fs = File.OpenWrite(Path.Combine(path, i + ".png"))) | |
rt.SaveAsPng(fs, pp.BackBufferWidth, pp.BackBufferHeight); | |
} | |
#else | |
g.RasterizerState = RasterizerState.CullCounterClockwise; | |
g.DepthStencilState = DepthStencilState.DepthRead; | |
g.BlendState = BlendState.AlphaBlend; | |
g.Clear(Color.Transparent); | |
model.Draw(); | |
g.Present(); | |
Thread.Sleep(1000 / 30); | |
#endif | |
} | |
} | |
} | |
} | |
class GraphicsDeviceService : IGraphicsDeviceService, IGraphicsDeviceManager | |
{ | |
public GraphicsDeviceService(GraphicsDevice g) | |
{ | |
this.GraphicsDevice = g; | |
} | |
public event EventHandler<EventArgs> DeviceCreated; | |
public event EventHandler<EventArgs> DeviceDisposing; | |
public event EventHandler<EventArgs> DeviceReset; | |
public event EventHandler<EventArgs> DeviceResetting; | |
public GraphicsDevice GraphicsDevice | |
{ | |
get; | |
private set; | |
} | |
public bool BeginDraw() | |
{ | |
return true; | |
} | |
public void CreateDevice() | |
{ | |
} | |
public void EndDraw() | |
{ | |
} | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment