UE4 UIの端だけにフェード処理を掛ける
やあ
UIの端っこだけフェードアウトしたいなーって思って作ったよ。
フェード処理をするためのマテリアル
線形グラデーションを掛け合わせて左右(上下)にかけてグラデーションさせてるだけ。
このマテリアルを右クリックしてインスタンスにしておくとパラメータを好きにいじれる。
注意
- UIで使う際に
TextureSampleParameter2D
のパラメータの名前を一致させる必要がある。 TextureSampleParameter2D
を最終カラーにつながないと下の画像のようになる。
UIで使う
RetainerBox
の下にフェード処理を掛けたいウィジェットを入れるだけ。
RetainerBox -> 詳細 -> エフェクト -> EffectMaterial
にさっき作ったマテリアルを割り当て、TextureParameter
にマテリアルのTextureSampleParameter2D
のパラメータ名を入れる。
結果
終わりです。
Blender python 骨をアーマチュアに追加する
やあ
同じボーン階層のキャラクターをいっぱい作った後に、骨を追加したいなって思って書いたよ。
※注意 : 今回はやってることはリーフボーンの追加なので、骨と骨の間に追加したい場合はちょっと書き換える必要があります。自分で使う機会があれば追記します。
スクリプト
import bpy from typing import List, Any def get_obj(name : str): return bpy.data.objects.get(name) bpy.ops.object.mode_set(mode='OBJECT') """ 骨を追加したいアーマチュアの名前 """ target_obj_names = [ "Armature_A", "Armature_B" ] class NewBoneSpec: def __init__(self, NewBoneName: str, ParentName: str, Head: List[float] = [0.0, 0.0, 0.0], Tail: List[float] = [0.0, 0.0, 1.0], Roll: float = 0.0, bAutoTransform: bool = False ): self.parent = ParentName self.new_bone = NewBoneName self.head = Head self.tail = Tail self.roll = Roll self.bAutoTransform = bAutoTransform class NewBoneMaker: def __init__(self, Spec: NewBoneSpec, Armature: Any ): self.spec = Spec self.Armature = Armature def DoMake(self): if self.Armature: edit_bones = self.Armature.data.edit_bones if edit_bones: if not edit_bones.get(self.spec.new_bone): new_bone = edit_bones.new(self.spec.new_bone) if new_bone: parent = target_edit_bone.get(self.spec.parent) if parent: new_bone.parent = target_edit_bone.get(self.spec.parent) if self.spec.bAutoTransform: head = [new_bone.parent.tail[0], new_bone.parent.tail[1], new_bone.parent.tail[2]] new_bone.head = head tail = [head[0], head[1], head[2] + 1.0] new_bone.tail = tail new_bone.roll = 0.0 else: new_bone.head = new_bone_spec.head new_bone.tail = new_bone_spec.tail new_bone.roll = new_bone_spec.roll new_bone_specs = [ NewBoneSpec(NewBoneName="Weapon_R", ParentName="Hand_R", bAutoTransform=True), NewBoneSpec(NewBoneName="Weapon_L", ParentName="Hand_L", bAutoTransform=True), ] for target_obj_name in target_obj_names: target_armature = get_obj(target_obj_name) if target_armature: target_armature.select = True bpy.ops.object.mode_set(mode='EDIT') target_edit_bone = target_armature.data.edit_bones if target_edit_bone: for new_bone_spec in new_bone_specs: new_bone_maker = NewBoneMaker(new_bone_spec, target_armature) new_bone_maker.DoMake() target_armature.select = False bpy.ops.object.mode_set(mode='OBJECT')
使い方
target_obj_names
に骨を追加したいアーマチュアの名前を入れます。new_bone_specs
に、新しく追加したい骨の名前と、その親の骨の名前を入れます。
このとき、トランスフォームを手動で決めることもできます。
また、bAutoTransform = True
に指定すると、新しい骨が親の骨に対して垂直に追加されます。
- 実行
Blender python 骨を揃える
やあ
ブレンダーでキャラクターをいっぱい作った後にちょっと骨の位置を修正したいなーってなったときに書いた、骨を特定のアーマチュアに揃えるスクリプトだよ。
揃える元のアーマチュアがある場合
import bpy from typing import Dict, List def get_obj(name : str): return bpy.data.objects.get(name) def get_children(result: Dict, target_bone) -> List: if len(target_bone.children) == 0: return [] child_name = [] next_tasks = [] for child in target_bone.children: next_tasks.append(child) child_name.append(child.name) if target_bone.name in result: result[target_bone.name] += child_name else: result[target_bone.name] = child_name for child in next_tasks: get_children(result, child) bpy.ops.object.mode_set(mode='OBJECT') """ ---- ソースオブジェクト ---- """ source_obj_name = "source_armature_name" source_armature = get_obj(source_obj_name) source_armature.select = True root_bone_name = "Root" """ ---- 処理をしたいオブジェクトの名前 """ target_obj_names = [ "Armature_A", "Armature_B" ] """ ---- 処理をしたくない骨の親の名前 ---- 例 : 親 : Hand 子 : Thumb, Index, Middle, Ring, Pinky となっているときに、 Handを追加すると、子が無視されます """ ignore_bones_parent_names = [ ] """ ---- 無視したい骨の名前 ---- """ ignore_bone_names = [ ] """ ---- 無視したい骨の名前の一部 ---- """ ignore_part_of_names = [ "IK_", "C_" ] """ ---- トランスフォーム : ヘッドを無視する骨の名前 ---- """ ignore_head_bone_names = [ ] """ ---- トランスフォーム : テイルを無視する骨の名前 ---- """ ignore_tail_bone_names = [ ] """ ---- トランスフォーム : ロールを無視する骨の名前 ---- """ ignore_roll_bone_names = [ ] is_debug = True for target_obj_name in target_obj_names: target_armature = get_obj(target_obj_name) if target_armature: if is_debug: print(target_armature) target_armature.select = True bpy.ops.object.mode_set(mode='EDIT') root_bone = target_armature.pose.bones.get(root_bone_name) if root_bone: children = dict() get_children(children, root_bone) for parent_name, childs in children.items(): if parent_name in ignore_bones_parent_names: continue for bone_name in childs: if bone_name in ignore_bone_names: continue is_found_ignore_bone = False for ignore_part_of_name in ignore_part_of_names: if ignore_part_of_name in bone_name: is_found_ignore_bone = True break if is_found_ignore_bone: continue target_bone = target_armature.data.edit_bones.get(bone_name) if target_bone: source_align_bone = source_armature.data.edit_bones.get(bone_name) if source_align_bone: if parent_name not in ignore_head_bone_names: target_bone.head = [source_align_bone.head[0], source_align_bone.head[1], source_align_bone.head[2]] if parent_name not in ignore_tail_bone_names: target_bone.tail = [source_align_bone.tail[0], source_align_bone.tail[1], source_align_bone.tail[2]] if parent_name not in ignore_roll_bone_names: target_bone.roll = source_align_bone.roll else: if is_debug: print("root bone is None at : " + target_armature.name) bpy.ops.object.mode_set(mode='OBJECT') target_armature.select = False else: if is_debug: print("Target armature is None at : " + target_obj_name) bpy.ops.object.mode_set(mode='OBJECT')
# 指定するのが面倒だから全オブジェクトについて処理したい場合
import bpy from typing import Dict, List def get_obj(name : str): return bpy.data.objects[name] def get_children(result: Dict, target_bone) -> List: if len(target_bone.children) == 0: return [] child_name = [] next_tasks = [] for child in target_bone.children: next_tasks.append(child) child_name.append(child.name) if target_bone.name in result: result[target_bone.name] += child_name else: result[target_bone.name] = child_name for child in next_tasks: get_children(result, child) bpy.ops.object.mode_set(mode='OBJECT') """ ---- ソースオブジェクト ---- """ source_obj_name = "Source_Armature" source_armature = get_obj(source_obj_name) source_armature.select = True root_bone_name = "Root" """ ---- 処理をしたくない骨の親の名前 ---- 例 : 親 : Hand 子 : Thumb, Index, Middle, Ring, Pinky となっているときに、 Handを追加すると、子が無視されます """ ignore_bones_parent_names = [ ] """ ---- 無視したい骨の名前 ---- """ ignore_bone_names = [ ] """ ---- 無視したい骨の名前の一部 ---- """ ignore_part_of_names = [ "IK_", "C_" ] """ ---- トランスフォーム : ヘッドを無視する骨の名前 ---- """ ignore_head_bone_names = [ ] """ ---- トランスフォーム : テイルを無視する骨の名前 ---- """ ignore_tail_bone_names = [ ] """ ---- トランスフォーム : ロールを無視する骨の名前 ---- """ ignore_roll_bone_names = [ ] is_debug = True for obj in bpy.data.objects: if obj.type == "ARMATURE": target_armature = get_obj(obj.name) if target_armature: if is_debug: print(target_armature) target_armature.select = True bpy.ops.object.mode_set(mode='EDIT') root_bone = target_armature.pose.bones.get(root_bone_name) if root_bone: children = dict() get_children(children, root_bone) for parent_name, childs in children.items(): if parent_name in ignore_bones_parent_names: continue for bone_name in childs: if bone_name in ignore_bone_names: continue is_found_ignore_bone = False for ignore_part_of_name in ignore_part_of_names: if ignore_part_of_name in bone_name: is_found_ignore_bone = True break if is_found_ignore_bone: continue target_bone = target_armature.data.edit_bones.get(bone_name) if target_bone: source_align_bone = source_armature.data.edit_bones.get(bone_name) if source_align_bone: if parent_name not in ignore_head_bone_names: target_bone.head = [source_align_bone.head[0], source_align_bone.head[1], source_align_bone.head[2]] if parent_name not in ignore_tail_bone_names: target_bone.tail = [source_align_bone.tail[0], source_align_bone.tail[1], source_align_bone.tail[2]] if parent_name not in ignore_roll_bone_names: target_bone.roll = source_align_bone.roll else: if is_debug: print("root bone is None " + target_armature.name) bpy.ops.object.mode_set(mode='OBJECT') target_armature.select = False else: if is_debug: print("Target armature is None " + obj.name) bpy.ops.object.mode_set(mode='OBJECT')
値を入力して揃える
import bpy align_bone_name = "Hand_L" target_obj_names = [ "Armature_A", "Armature_B" ] def get_obj(name : str): return bpy.data.objects.get(name) source_align_bone_head = [-1.3189, 0.1459, 1.9255] source_align_bone_tail = [-1.3189, -0.2293, 1.9255] source_align_bone_roll = 0.0 if source_align_bone_head == source_align_bone_tail: print(""" -------------- Warning. -------------- The head vector matches the tail vector. This will cause align_bone to be removed. So, this script is cancelled. -------------------------------------- """) else: for target_obj_name in target_obj_names: target_armature = get_obj(target_obj_name) if target_armature: target_armature.select = True print(target_armature) bpy.ops.object.mode_set(mode='EDIT') target_bone = target_armature.data.edit_bones.get(align_bone_name) if target_bone: target_bone.head = source_align_bone_head target_bone.tail = source_align_bone_tail target_bone.roll = source_align_bone_roll bpy.ops.object.mode_set(mode='OBJECT') target_armature.select = False
Gimp リング状の衝撃破テクスチャを描く
楕円選択で正円に選択。
グラデーションが入ったブラシで選択範囲の外側に沿って塗る。
消しゴムで適当に消していく。
完成。
Blender UE4のエフェクトで使うトルネード用のメッシュの作り方
半球
Shift+A
→メッシュ
→UV Sphere
Scale : x : 100, y : 100, z : 100
Ctrl+1
(Add Subdivision)→Apply
Add Modifier
→SimpleDeform
Axis : Z
, Angle: 145
上を選択して、外側をCtrl+左クリック
Sで縮小。
何回か縮小したら終わり。
注意
UVは初期状態のまま拡大。
変に展開すると見た目がおかしくなります。
UE4 Niagara LockAxis
パラメータのパーティクル属性に
SpriteFacing
を追加。
パラメータに追加した
SpriteFacing
をパーティクル更新にドラッグアンドドロップ。
レンダリングをクリックして、
FacingMode
をCustomFacingVector
に設定。
パーティクル更新に追加した
SpriteFacing
をいじると軸固定できます。
x = 1.0でx軸固定。
y = 1.0でy軸固定。
z = 1.0でz軸固定。