pgraph: Support hardware instancing in BillboardEffect and CompassEffect
This commit is contained in:
parent
bd7b6d8fe7
commit
e13756f43e
|
|
@ -140,7 +140,25 @@ cull_callback(CullTraverser *trav, CullTraverserData &data,
|
|||
camera_transform = trav->get_camera_transform()->invert_compose(_look_at.get_net_transform());
|
||||
}
|
||||
|
||||
compute_billboard(node_transform, modelview_transform, camera_transform);
|
||||
if (data._instances == nullptr) {
|
||||
compute_billboard(node_transform, modelview_transform, camera_transform);
|
||||
}
|
||||
else {
|
||||
// Compute the billboard effect for every instance individually.
|
||||
InstanceList *instances = new InstanceList(*data._instances);
|
||||
data._instances = instances;
|
||||
|
||||
for (InstanceList::Instance &instance : *instances) {
|
||||
CPT(TransformState) inst_node_transform = node_transform;
|
||||
CPT(TransformState) inst_modelview_transform = modelview_transform->compose(instance.get_transform());
|
||||
compute_billboard(inst_node_transform, inst_modelview_transform, camera_transform);
|
||||
|
||||
instance.set_transform(instance.get_transform()->compose(inst_node_transform));
|
||||
}
|
||||
|
||||
// We've already applied this onto the instances.
|
||||
node_transform = TransformState::make_identity();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -120,20 +120,56 @@ cull_callback(CullTraverser *trav, CullTraverserData &data,
|
|||
return;
|
||||
}
|
||||
|
||||
CPT(TransformState) true_net_transform = data.get_net_transform(trav);
|
||||
CPT(TransformState) want_net_transform = true_net_transform;
|
||||
adjust_transform(want_net_transform, node_transform, data.node());
|
||||
if (data._instances == nullptr) {
|
||||
CPT(TransformState) true_net_transform = data.get_net_transform(trav);
|
||||
CPT(TransformState) want_net_transform = true_net_transform;
|
||||
adjust_transform(want_net_transform, node_transform, data.node());
|
||||
|
||||
// Now compute the transform that will convert true_net_transform to
|
||||
// want_transform. This is inv(true_net_transform) * want_transform.
|
||||
CPT(TransformState) compass_transform =
|
||||
true_net_transform->invert_compose(want_net_transform);
|
||||
// Now compute the transform that will convert true_net_transform to
|
||||
// want_transform. This is inv(true_net_transform) * want_transform.
|
||||
CPT(TransformState) compass_transform =
|
||||
true_net_transform->invert_compose(want_net_transform);
|
||||
|
||||
// And modify our local node's apparent transform so that
|
||||
// true_net_transform->compose(new_node_transform) produces the same result
|
||||
// we would have gotten had we actually computed
|
||||
// want_transform->compose(orig_node_transform).
|
||||
node_transform = compass_transform->compose(node_transform);
|
||||
// And modify our local node's apparent transform so that
|
||||
// true_net_transform->compose(new_node_transform) produces the same result
|
||||
// we would have gotten had we actually computed
|
||||
// want_transform->compose(orig_node_transform).
|
||||
node_transform = compass_transform->compose(node_transform);
|
||||
}
|
||||
else {
|
||||
// Compute the billboard effect for every instance individually.
|
||||
InstanceList *instances = new InstanceList(*data._instances);
|
||||
data._instances = instances;
|
||||
|
||||
CPT(TransformState) parent_net_transform = data.get_net_transform(trav);
|
||||
CPT(TransformState) invert_net_transform = parent_net_transform->get_inverse();
|
||||
|
||||
// We make use of the fact that we know adjust_transform() does not modify
|
||||
// its node_transform parameter.
|
||||
CPT(TransformState) node_transform_copy = node_transform;
|
||||
if (node_transform_copy->is_identity()) {
|
||||
// Slightly optimized case.
|
||||
for (InstanceList::Instance &instance : *instances) {
|
||||
CPT(TransformState) true_net_transform = parent_net_transform->compose(instance.get_transform());
|
||||
CPT(TransformState) want_net_transform = true_net_transform;
|
||||
adjust_transform(want_net_transform, node_transform_copy, data.node());
|
||||
|
||||
instance.set_transform(invert_net_transform->compose(want_net_transform));
|
||||
}
|
||||
}
|
||||
else {
|
||||
// We apply the node_transform to the instances.
|
||||
node_transform = TransformState::make_identity();
|
||||
|
||||
for (InstanceList::Instance &instance : *instances) {
|
||||
CPT(TransformState) true_net_transform = parent_net_transform->compose(instance.get_transform());
|
||||
CPT(TransformState) want_net_transform = true_net_transform;
|
||||
adjust_transform(want_net_transform, node_transform_copy, data.node());
|
||||
|
||||
instance.set_transform(invert_net_transform->compose(want_net_transform)->compose(node_transform_copy));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
Loading…
Reference in New Issue