創作內容

0 GP

2/23,實況事前規劃及今日實況產出(.vmd很難節選片段舞蹈播放,用取巧方式供參考)

作者:李兒諳│2024-02-24 09:33:25│巴幣:0│人氣:123
對之前被我坑的說聲抱歉
我之前貼的原神官網MMD模型是日文的
如果你語言不用日文模型會載入失敗
但看起來就像是中文,所以可能會debug de很久
原神模型官方載點建議用這個
或者是從這邊一步一步點進去
它模型沒辦法安全下載,但可以在...那邊按保留
或者是複製下載連結再貼一次即可

雖然是簡體中文,但使用起來跟繁體中文似乎沒什麼差異
唔,雖然我只有測試女主角而已
至少不會碰上像日文的問題
更多模型可以關注 模之屋 的 原神 帳號
(星穹鐵道印象中也有)

這次實況是用3D模型仿臥龍吟戰鬥系統
先說些題外話:我星穹鐵道2.1會抽砂金六魂,可以留個好友位
(不過要是沒抽到或差一點的話要不要補還不清楚)
為什麼不是抽黃泉啊,黃泉在2.0實裝後
我覺得模型看起來沒有說很差
可能之前是斜側面的關係
還以為跟希兒很像
我覺得黃泉背面,可能是髪飾的關係
感覺頭髮看起來還不錯

主要原因是我分身抽主C已經體驗得差不多了
(其實分身抽輔助也體驗了
而且高魂輔助,阮‧梅體驗算獨一檔的好了)
而且分身只湊個6+1或6+0主C
因為幾乎沒有拐,雖然我現在有四個分身都有停雲了
其實混沌回憶還是不太好打的
還是要主帳號人物比較齊全時再抽6魂主C
感覺才會好很多
有個原因是,如果我分身抽了某個六魂主C
我主帳號再抽同個六魂主C
感覺上是有些虧的
星穹鐵道還不知道會不會出角色皮膚
如果出的話
大致上也不用留抽等著可能出現未來的雷電芽衣變體了
而且其實我本尊遲遲不抽的主要顧慮是
萬一星穹鐵道哪天,可能是3.X版本時
又多了只Up一次之後就進普池的角色
為了避免之後很難補單一特定星魂
因此要囤抽防那狀況
不然哪天發財了又不是發大財
有機會全角色六星魂時,額外開銷會很難估算

那既然主C要留著可能以後給主帳號抽
那分身就只能挑輔助或生存了
花火我覺得六魂對於我而言
可能不足以讓我的分身們好打後面可能新增的關卡
所以我目前是蠻期待六魂砂金的
只要他的AI是一直放戰技疊盾
再不然就是我調成手動模式
我想我分身應該就打得動後面能借人的關卡

實況具體規劃
13:00~13:20 載入多個不同的MMD模型看看會不會耗時很久
先只載入四個, 符玄、卡芙卡、景元、阮‧梅 好了
因為2D的時候也只有先設定四個戰鬥角色
(這段已於上午完成,不過載入過程肉眼看得見,就3D模型從沒有貼圖到有貼圖時這樣)

13:20~15:00 處理模型縮放或者是調整攝影機
讓同個畫面可以顯示多個MMD模型
(調整攝影機,就MMD模型載入的範例用到的
orbitcontrol那個就可以手動用滑鼠滾輪調整攝影機距離了
哦,查了下
滑鼠滾輪是遠近,左鍵按住後移動是旋轉,右鍵按住後是鏡頭平移

模型縮放還在研究中
11:30時研究出來了
mesh.scale.set(0.5,0.5,0.5);這樣就縮小成八分之一的大小了
應該啦,也就是三個維度都縮一半比例)

由於這兩階段上午沒實況時研究還算順利
所以更改為
13:00~14:00 嘗試MMD模型只播.vmd舞步檔的某一時間段的內容
(以後可能戰鬥動畫直接做成.vmd檔
我以前沒做過3D戰鬥動畫,還不清楚這樣是否會有什麼致命問題)

14:00~15:00 併入仿臥龍吟戰鬥系統中
試著顯示攻擊動畫來完成一場只有普攻的完整的戰鬥

實況時間只有13:00~15:00

唔,這邊耗時可能是多了些
但主要原因是我以前也沒接觸過three.js
不太確定這邊指令要怎麼下
所以運氣不好的話可能今天還沒辦法處理完畢

如果順利的話,就試著用.vmd檔充當攻擊動作
然後再研究看看攝影機鏡頭要怎麼操作
戰鬥時才拉近,平時顯示敵我雙方的模型
然後再回到之前仿臥龍吟2D的戰鬥過程播放這樣

嗯,目前會是空白的背景
因為我還沒下載場地模型
當然目前我也還不會製作

那現在到實況開始前我會先輕鬆滴找下相關資料
(輕鬆的意思是可能找著找著就做別的事去了)
找累了可能就趕下原神,完成新年相關活動這樣
(沒抽到閒雲,但抽到雷閒雲、嘉明了
所以新年活動也不急著完成
這次新年活動主線有些長啊!!
我解好幾天了,歷練點到湊齊四個每日委託就收手的關係)

我原神目前幾乎處於荒廢狀態了
(要是不荒廢的話,也不會在3.2版本左右57等,到現在才58等這樣)
我原神可能以後也不充了
上次娜維婭時,想說清首充,運氣還算不錯是得到了神里綾華
不過娜維婭練完後就遲遲沒練、沒消耗樹脂就是了

我現在一天大概早上花個50分鐘清光星穹鐵道六個帳號的行動力
大致上就把整天的事情忙完了
前陣子想說有點閒就玩下崩壞3rd
不過覺得崩壞3rd清行動力很麻煩
抽人物看起來很遙遠,大概玩了九天之後就沒什麼動力了

雖然我一天還會點兩次落櫻散華抄跟兩次臥龍吟這樣
有角色生日時登入下少女歌劇Re-live
因為現在星穹鐵道主帳號沒怎麼在鋤大地了
一個星期撥些時間完成六個帳號的歷戰餘響跟模擬宇宙這樣
偶爾打混沌回憶、虛構敘事
大致上就蠻悠閒的

實況產出
嗯,.vmd檔就是用來播放完整影片用的
它預設沒有控制播放特定時間段的功能
所以要播放特定片段
似乎得靠自己手動調整時間來處理
等下index.html有改變開始時間的範例
那結束的話理論上就是算時間到了後
不再繼續運行requestAnimationFrame( animate );即可
網路上有人有改良的MMD舞步播放調整
改成可以中途停下來
但要調成某個時間點開始比較難
它繪製主要靠MMDAnimationHelper.update(秒數)
但那個秒數是浮點數為單位

所以要不停的刷新,一般會使用clock.getDelta()
我估計是每次只更新隔0.03秒左右骨骼位置
因此值只要大過2秒以上動作就看起來像lag
每次只差0.7秒的話還算有加速的效果
所以我的解決方法才是先讓影片空轉幾秒(空白的,看起來像當機了)
才開始播放動畫

要定格在某個姿勢,應該是需要用.vpd檔
再配合MMDAnimationHelper.pose()使用
理論上來說應該也可以把程式寫死
就把MMD模型的哪個骨骼移到、旋轉到哪邊這樣
不過手動寫死的方法要怎麼寫我目前也還不知道
只是我看原始碼有部份看起來是有這感覺

----重點我用別的顏色標出來----
----藍色是載入多個不同MMD檔的寫法,就注意座標要移一下----
----藍色載入的MMD模型寫法是載入靜態的,通常不是A-pose就是T-pose----
----A-pose就是雙手大約擺在45度角的位置,T-pose就是雙手平舉----
----聽說新手學建模,一般會使用T-pose,因為比較好建模的樣子-----
----棕色是讓時間空轉個幾秒鐘,再開始播放動畫的寫法----------
----原則上來說模型檔的取得要自己想辦法----
----熱門人物的MMD模型,網路上應該還算好找----
-----------------目前用的index.html內容如下--------------------------

<!DOCTYPE html>
<html lang="en">
<head>
<title>three.js webgl - loaders - MMD loader</title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
<link type="text/css" rel="stylesheet" href="main.css">
<style>
body {
background-color: #fff;
color: #444;
}
a {
color: #08f;
}
</style>
</head>

<body>
<div id="info">
<a href="https://threejs.org" target="_blank" rel="noopener">three.js</a> - MMDLoader test<br />
<a href="https://github.com/mrdoob/three.js/tree/master/examples/models/mmd#readme" target="_blank" rel="noopener">MMD Assets license</a><br />
Copyright
<a href="https://sites.google.com/view/evpvp/" target="_blank" rel="noopener">Model Data</a>
<a href="http://www.nicovideo.jp/watch/sm13147122" target="_blank" rel="noopener">Dance Data</a>
</div>

<script src="jsm/libs/ammo.wasm.js"></script>

<script type="importmap">
{
"imports": {
"three": "../build/three.module.js",
"three/addons/": "./jsm/"
}
}
</script>

<script type="module">

import * as THREE from 'three';

import Stats from 'three/addons/libs/stats.module.js';
import { GUI } from 'three/addons/libs/lil-gui.module.min.js';

import { OrbitControls } from 'three/addons/controls/OrbitControls.js';
import { OutlineEffect } from 'three/addons/effects/OutlineEffect.js';
import { MMDLoader } from 'three/addons/loaders/MMDLoader.js';
import { MMDAnimationHelper } from 'three/addons/animation/MMDAnimationHelper.js';

let stats;

let mesh, camera, scene, renderer, effect;
let helper, ikHelper, physicsHelper;

const clock = new THREE.Clock();

Ammo().then( function ( AmmoLib ) {

Ammo = AmmoLib;

init();
clock.getDelta();
setTimeout(() => {
  console.log("Delayed for 4 second.");
animate();
}, 4000);

} );


function init() {

const container = document.createElement( 'div' );
document.body.appendChild( container );

camera = new THREE.PerspectiveCamera( 45, window.innerWidth / window.innerHeight, 1, 2000 );
camera.position.z = 30;

// scene

scene = new THREE.Scene();
scene.background = new THREE.Color( 0xffffff );

const gridHelper = new THREE.PolarGridHelper( 30, 0 );
gridHelper.position.y = - 10;
scene.add( gridHelper );

const ambient = new THREE.AmbientLight( 0xaaaaaa, 3 );
scene.add( ambient );

const directionalLight = new THREE.DirectionalLight( 0xffffff, 3 );
directionalLight.position.set( - 1, 1, 1 ).normalize();
scene.add( directionalLight );

//

renderer = new THREE.WebGLRenderer( { antialias: true } );
renderer.setPixelRatio( window.devicePixelRatio );
renderer.setSize( window.innerWidth, window.innerHeight );
container.appendChild( renderer.domElement );

effect = new OutlineEffect( renderer );

// STATS

stats = new Stats();
container.appendChild( stats.dom );

// model

function onProgress( xhr ) {

if ( xhr.lengthComputable ) {

const percentComplete = xhr.loaded / xhr.total * 100;
console.log( Math.round( percentComplete, 2 ) + '% downloaded' );

}

}


const modelFile = 'Jing Yuan/景元.pmx';
const vmdFiles = [ 'wavefile_v2.vmd' ];

helper = new MMDAnimationHelper( {
afterglow: 2.0
} );

const loader = new MMDLoader();

loader.loadWithAnimation( modelFile, vmdFiles, function ( mmd ) {

mesh = mmd.mesh;
mesh.position.y = - 10;
scene.add( mesh );

helper.add( mesh, {
animation: mmd.animation,
physics: true
} );

ikHelper = helper.objects.get( mesh ).ikSolver.createHelper();
ikHelper.visible = false;
scene.add( ikHelper );

physicsHelper = helper.objects.get( mesh ).physics.createHelper();
physicsHelper.visible = false;
scene.add( physicsHelper );

initGui();

}, onProgress, null );

loader.load(

'Kafka/卡芙卡.pmx',

function ( mesh ) {
mesh.position.x = - 20;
mesh.scale.set(0.5,0.5,0.5);
scene.add( mesh );

},

function ( xhr ) {

console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

},

function ( error ) {

console.log( 'An error happened' );

}
);

loader.load(

'Ruan Mei/阮梅.pmx',

function ( mesh ) {
mesh.position.x = + 20;
scene.add( mesh );

},

function ( xhr ) {

console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

},

function ( error ) {

console.log( 'An error happened' );

}
);

loader.load(
'Fu Xuan/符玄.pmx',
function ( mesh ) {
mesh.position.x = + 40;
scene.add( mesh );
initGui();
},
function ( xhr ) {

console.log( ( xhr.loaded / xhr.total * 100 ) + '% loaded' );

},
// called when loading has errors
function ( error ) {

console.log( 'An error happened' );

}
);

const controls = new OrbitControls( camera, renderer.domElement );
controls.minDistance = 10;
controls.maxDistance = 100;

window.addEventListener( 'resize', onWindowResize );

function initGui() {

const api = {
'animation': true,
'ik': true,
'outline': true,
'physics': true,
'show IK bones': false,
'show rigid bodies': false
};

const gui = new GUI();

gui.add( api, 'animation' ).onChange( function () {

helper.enable( 'animation', api[ 'animation' ] );

} );

gui.add( api, 'ik' ).onChange( function () {

helper.enable( 'ik', api[ 'ik' ] );

} );

gui.add( api, 'outline' ).onChange( function () {

effect.enabled = api[ 'outline' ];

} );

gui.add( api, 'physics' ).onChange( function () {

helper.enable( 'physics', api[ 'physics' ] );

} );

gui.add( api, 'show IK bones' ).onChange( function () {

ikHelper.visible = api[ 'show IK bones' ];

} );

gui.add( api, 'show rigid bodies' ).onChange( function () {

if ( physicsHelper !== undefined ) physicsHelper.visible = api[ 'show rigid bodies' ];

} );

}

}

function onWindowResize() {

camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();

effect.setSize( window.innerWidth, window.innerHeight );

}

function animate() {

requestAnimationFrame( animate );

stats.begin();
render();
stats.end();

}

function render() {
helper.update( clock.getDelta());
//helper.update( clock.getDelta() +0.09);
//會變成加速效果,因為啟動時鐘後,時間持續增加又再加上個常數0.09秒這樣


effect.render( scene, camera );

}

</script>

</body>
</html>
引用網址:https://home.gamer.com.tw/TrackBack.php?sn=5887923
All rights reserved. 版權所有,保留一切權利

相關創作

留言共 0 篇留言

我要留言提醒:您尚未登入,請先登入再留言

喜歡★y541258 可決定是否刪除您的留言,請勿發表違反站規文字。

前一篇:2/22,問題─星穹鐵道... 後一篇:3/1,2.0版本下半鋤...

追蹤私訊切換新版閱覽

作品資料夾

hyzgdivina喜歡虹咲的LLer
我的小屋裡有很多又香又甜的Hoenn繪師虹咲漫畫翻譯喔!歡迎LoveLiver來我的小屋裡坐坐~看更多我要大聲說1分內


face基於日前微軟官方表示 Internet Explorer 不再支援新的網路標準,可能無法使用新的應用程式來呈現網站內容,在瀏覽器支援度及網站安全性的雙重考量下,為了讓巴友們有更好的使用體驗,巴哈姆特即將於 2019年9月2日 停止支援 Internet Explorer 瀏覽器的頁面呈現和功能。
屆時建議您使用下述瀏覽器來瀏覽巴哈姆特:
。Google Chrome(推薦)
。Mozilla Firefox
。Microsoft Edge(Windows10以上的作業系統版本才可使用)

face我們了解您不想看到廣告的心情⋯ 若您願意支持巴哈姆特永續經營,請將 gamer.com.tw 加入廣告阻擋工具的白名單中,謝謝 !【教學】