mirror of
https://github.com/DaanVandenBosch/phantasmal-world.git
synced 2025-04-04 06:28:28 +08:00
Improved rendering of entities that use additive blending in NPCs/Objects panels.
This commit is contained in:
parent
eb5b539b6d
commit
78c18eb1e9
@ -151,7 +151,6 @@ Features that are in ***bold italics*** are planned but not yet implemented.
|
||||
|
||||
## Bugs
|
||||
|
||||
- [NPC/Object Manipulation](#npcobject-manipulation): Entities in NPCs/Objects panels with additive blending aren't rendered correctly.
|
||||
- [Load Quest](#load-quest): Can't parse quest 125 White Day
|
||||
- [Script Assembly Editor](#script-assembly-editor): Go to definition doesn't work in RT (#231)
|
||||
- When a modal dialog is open, global keybindings should be disabled
|
||||
|
@ -2,10 +2,10 @@ import { initialize_application } from "./index";
|
||||
import { LogHandler, LogManager } from "../core/Logger";
|
||||
import { FileSystemHttpClient } from "../../test/src/core/FileSystemHttpClient";
|
||||
import { timeout } from "../../test/src/utils";
|
||||
import { StubThreeRenderer } from "../../test/src/core/rendering/StubThreeRenderer";
|
||||
import { Random } from "../core/Random";
|
||||
import { Severity } from "../core/Severity";
|
||||
import { StubClock } from "../../test/src/core/StubClock";
|
||||
import { STUB_THREE_RENDERER } from "../../test/src/core/rendering/StubThreeRenderer";
|
||||
|
||||
for (const path of [undefined, "/viewer", "/quest_editor", "/hunt_optimizer"]) {
|
||||
const with_path = path == undefined ? "without specific path" : `with path ${path}`;
|
||||
@ -28,7 +28,7 @@ for (const path of [undefined, "/viewer", "/quest_editor", "/hunt_optimizer"]) {
|
||||
new FileSystemHttpClient(),
|
||||
new Random(() => 0.27),
|
||||
new StubClock(new Date("2020-01-01T15:40:20Z")),
|
||||
() => new StubThreeRenderer(),
|
||||
() => STUB_THREE_RENDERER,
|
||||
);
|
||||
|
||||
expect(app).toBeDefined();
|
||||
|
@ -22,7 +22,7 @@ CameraControls.install({
|
||||
},
|
||||
});
|
||||
|
||||
export interface DisposableThreeRenderer extends THREE.Renderer, Disposable {}
|
||||
export interface DisposableThreeRenderer extends THREE.WebGLRenderer, Disposable {}
|
||||
|
||||
/**
|
||||
* Uses THREE.js for rendering.
|
||||
|
@ -1,4 +1,11 @@
|
||||
import { HemisphereLight, PerspectiveCamera, Scene, Vector3 } from "three";
|
||||
import {
|
||||
DoubleSide,
|
||||
HemisphereLight,
|
||||
MeshBasicMaterial,
|
||||
PerspectiveCamera,
|
||||
Scene,
|
||||
Vector3,
|
||||
} from "three";
|
||||
import { EntityType } from "../../core/data_formats/parsing/quest/entities";
|
||||
import { create_entity_type_mesh } from "./conversion/entities";
|
||||
import { sequential } from "../../core/sequential";
|
||||
@ -40,19 +47,44 @@ export class EntityImageRenderer implements Disposable {
|
||||
(entity: EntityType): DisposablePromise<string> =>
|
||||
this.entity_asset_loader.load_geometry(entity).then(geometry =>
|
||||
this.entity_asset_loader.load_textures(entity).then(textures => {
|
||||
// First render a flat version of the model with the same color as the
|
||||
// background. Then render the final version on top of that. We do this to
|
||||
// somewhat fix issues with additive alpha blending on a transparent background.
|
||||
|
||||
scene.remove(...scene.children);
|
||||
scene.add(light);
|
||||
|
||||
const entity_model = create_entity_type_mesh(entity, geometry, textures);
|
||||
scene.add(entity_model);
|
||||
// Render the flat model.
|
||||
|
||||
const b_sphere = entity_model.geometry.boundingSphere!;
|
||||
const entity_model_bg = create_entity_type_mesh(
|
||||
entity,
|
||||
geometry,
|
||||
[],
|
||||
new MeshBasicMaterial({
|
||||
color: 0x262626,
|
||||
side: DoubleSide,
|
||||
}),
|
||||
);
|
||||
scene.add(entity_model_bg);
|
||||
|
||||
const b_sphere = entity_model_bg.geometry.boundingSphere!;
|
||||
camera.position.copy(camera_position);
|
||||
camera.position.multiplyScalar(b_sphere.radius * camera_dist_factor);
|
||||
camera.lookAt(b_sphere.center);
|
||||
|
||||
this.renderer.render(scene, camera);
|
||||
|
||||
scene.remove(entity_model_bg);
|
||||
|
||||
// Render the textured model.
|
||||
|
||||
const entity_model = create_entity_type_mesh(entity, geometry, textures);
|
||||
scene.add(entity_model);
|
||||
|
||||
this.renderer.autoClearColor = false;
|
||||
this.renderer.render(scene, camera);
|
||||
this.renderer.autoClearColor = true;
|
||||
|
||||
return this.renderer.domElement.toDataURL();
|
||||
}),
|
||||
),
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { QuestEntityModel } from "../../model/QuestEntityModel";
|
||||
import { BufferGeometry, DoubleSide, Mesh, MeshLambertMaterial, Texture } from "three";
|
||||
import { BufferGeometry, DoubleSide, Material, Mesh, MeshLambertMaterial, Texture } from "three";
|
||||
import { create_mesh } from "../../../core/rendering/conversion/create_mesh";
|
||||
import {
|
||||
entity_type_to_string,
|
||||
@ -31,12 +31,11 @@ export function create_entity_type_mesh(
|
||||
type: EntityType,
|
||||
geometry: BufferGeometry,
|
||||
textures: Texture[],
|
||||
): Mesh {
|
||||
const default_material = new MeshLambertMaterial({
|
||||
default_material: Material = new MeshLambertMaterial({
|
||||
color: is_npc_type(type) ? NPC_COLORS[ColorType.Normal] : OBJECT_COLORS[ColorType.Normal],
|
||||
side: DoubleSide,
|
||||
});
|
||||
|
||||
}),
|
||||
): Mesh {
|
||||
const mesh = create_mesh(geometry, textures, default_material, false);
|
||||
mesh.name = entity_type_to_string(type);
|
||||
return mesh;
|
||||
|
@ -4,7 +4,7 @@ import { CharacterClassAssetLoader } from "../../loading/CharacterClassAssetLoad
|
||||
import { FileSystemHttpClient } from "../../../../test/src/core/FileSystemHttpClient";
|
||||
import { ModelView } from "./ModelView";
|
||||
import { ModelRenderer } from "../../rendering/ModelRenderer";
|
||||
import { StubThreeRenderer } from "../../../../test/src/core/rendering/StubThreeRenderer";
|
||||
import { STUB_THREE_RENDERER } from "../../../../test/src/core/rendering/StubThreeRenderer";
|
||||
import { Random } from "../../../core/Random";
|
||||
import { ModelStore } from "../../stores/ModelStore";
|
||||
import { ModelToolBarView } from "./ModelToolBarView";
|
||||
@ -26,8 +26,9 @@ test("Renders correctly.", () =>
|
||||
disposer.add(new ModelController(store)),
|
||||
new ModelToolBarView(disposer.add(new ModelToolBarController(store))),
|
||||
new CharacterClassOptionsView(disposer.add(new CharacterClassOptionsController(store))),
|
||||
new ModelRenderer(store, new StubThreeRenderer()),
|
||||
new ModelRenderer(store, STUB_THREE_RENDERER),
|
||||
);
|
||||
|
||||
expect(view.element).toMatchSnapshot();
|
||||
}));
|
||||
})
|
||||
);
|
||||
|
@ -1,11 +1,11 @@
|
||||
import { DisposableThreeRenderer } from "../../../../src/core/rendering/ThreeRenderer";
|
||||
|
||||
export class StubThreeRenderer implements DisposableThreeRenderer {
|
||||
domElement: HTMLCanvasElement = document.createElement("canvas");
|
||||
export const STUB_THREE_RENDERER: DisposableThreeRenderer = {
|
||||
domElement: document.createElement("canvas"),
|
||||
|
||||
dispose(): void {} // eslint-disable-line
|
||||
dispose(): void {}, // eslint-disable-line
|
||||
|
||||
render(): void {} // eslint-disable-line
|
||||
render(): void {}, // eslint-disable-line
|
||||
|
||||
setSize(): void {} // eslint-disable-line
|
||||
}
|
||||
setSize(): void {}, // eslint-disable-line
|
||||
} as any;
|
||||
|
Loading…
Reference in New Issue
Block a user