paint: merge sculpt
This commit is contained in:
@@ -286,6 +286,7 @@ void export_arm_pack_assets(project_t *raw, asset_t_array_t
|
||||
void export_arm_run_swatches(char *path);
|
||||
void import_asset_run(char *path, f32 drop_x, f32 drop_y, bool show_box, bool hdr_as_envmap, void (*done)(void));
|
||||
void make_particle_mask(node_shader_t *kong);
|
||||
material_data_t *make_particle_get_bullet_material();
|
||||
void uniforms_ext_init();
|
||||
void render_path_deferred_init();
|
||||
void render_path_deferred_commands();
|
||||
@@ -683,11 +684,18 @@ void render_path_raytrace_raytrace_init(char *shader_nam
|
||||
void render_path_raytrace_draw(bool use_live_layer);
|
||||
node_shader_context_t *sculpt_make_sculpt_run(material_t *data, material_context_t *matcon);
|
||||
void sculpt_make_mesh_run(node_shader_t *kong, slot_layer_t_array_t *sculpt_layers, i32_array_t *sculpt_indices);
|
||||
void sculpt_import_mesh_pack_to_texture(mesh_data_t *mesh, gpu_texture_t *target);
|
||||
void sculpt_init_sculpt_texture(slot_layer_t *l, mesh_data_t *md);
|
||||
void sculpt_make_paint_run(node_shader_t *kong);
|
||||
bool sculpt_layer_has_visible_masks(slot_layer_t *l);
|
||||
bool sculpt_mask_value(node_shader_t *kong, slot_layer_t *l, char *out_var, bool attrib, slot_layer_t *skip);
|
||||
i32 sculpt_object_vertex_offset(mesh_object_t *o);
|
||||
void sculpt_import_mesh_pack_to_texture(gpu_texture_t *target);
|
||||
void sculpt_init_sculpt_texture(slot_layer_t *l);
|
||||
void sculpt_init_meshes();
|
||||
void sculpt_init();
|
||||
void sculpt_layers_create_sculpt_layer();
|
||||
void render_path_sculpt_displace_pass(char *texpaint_sculpt);
|
||||
void render_path_sculpt_commands();
|
||||
void render_path_sculpt_snapshot_gbuffer();
|
||||
void render_path_sculpt_begin();
|
||||
void ui_statusbar_init();
|
||||
void ui_statusbar_render_ui();
|
||||
|
||||
@@ -92,7 +92,9 @@ string_array_t *make_paint_color_attachments() {
|
||||
}
|
||||
|
||||
node_shader_context_t *make_paint_run(material_t *data, material_context_t *matcon) {
|
||||
if (g_context->layer->texpaint_sculpt != NULL) {
|
||||
bool picking_tool = g_context->tool == TOOL_TYPE_COLORID || g_context->tool == TOOL_TYPE_PICKER || g_context->tool == TOOL_TYPE_MATERIAL ||
|
||||
g_context->tool == TOOL_TYPE_CURSOR;
|
||||
if (g_context->layer->texpaint_sculpt != NULL && !picking_tool) {
|
||||
return sculpt_make_sculpt_run(data, matcon);
|
||||
}
|
||||
|
||||
@@ -594,44 +596,7 @@ node_shader_context_t *make_paint_run(material_t *data, material_context_t *matc
|
||||
parser_material_triplanar = false;
|
||||
parser_material_sample_keep_aspect = false;
|
||||
|
||||
{
|
||||
slot_layer_t_array_t *sculpt_layers = any_array_create_from_raw((void *[]){}, 0);
|
||||
i32_array_t *sculpt_indices = i32_array_create(0);
|
||||
for (i32 i = 0; i < g_project->_->layers->length; ++i) {
|
||||
slot_layer_t *l = g_project->_->layers->buffer[i];
|
||||
if (l->texpaint_sculpt != NULL && slot_layer_is_visible(l)) {
|
||||
any_array_push(sculpt_layers, l);
|
||||
i32_array_push(sculpt_indices, i);
|
||||
}
|
||||
}
|
||||
i32 scount = sculpt_layers->length;
|
||||
if (scount > 0) {
|
||||
i32 idx0 = sculpt_indices->buffer[0];
|
||||
node_shader_add_constant(kong, string("texpaint_sculpt_size%d: float2", idx0), string("_size(_texpaint_sculpt%d)", idx0));
|
||||
for (i32 i = 0; i < scount; ++i) {
|
||||
i32 idx = sculpt_indices->buffer[i];
|
||||
node_shader_add_texture(kong, string("texpaint_sculpt%d", idx), string("_texpaint_sculpt%d", idx));
|
||||
}
|
||||
if (scount > 1) {
|
||||
node_shader_add_texture(kong, "texpaint_sculpt_base", "_texpaint_sculpt_base");
|
||||
}
|
||||
|
||||
node_shader_write_attrib_vert(kong, string("var sculpt_uv_paint: uint2 = uint2(uint(float(vertex_id()) %% constants.texpaint_sculpt_size%d.x), "
|
||||
"uint(float(vertex_id()) / constants.texpaint_sculpt_size%d.y));",
|
||||
idx0, idx0));
|
||||
|
||||
node_shader_write_attrib_vert(kong, string("var sculpt_pos_paint: float4 = texpaint_sculpt%d[sculpt_uv_paint];", idx0));
|
||||
for (i32 i = 1; i < scount; ++i) {
|
||||
i32 idx = sculpt_indices->buffer[i];
|
||||
node_shader_write_attrib_vert(
|
||||
kong, string("sculpt_pos_paint = sculpt_pos_paint + texpaint_sculpt%d[sculpt_uv_paint] - texpaint_sculpt_base[sculpt_uv_paint];", idx));
|
||||
}
|
||||
node_shader_write_attrib_vert(kong, "output.ndc = constants.WVP * float4(sculpt_pos_paint.xyz, 1.0);");
|
||||
if (kong->frag_wposition) {
|
||||
node_shader_write_attrib_vert(kong, "output.wposition = (constants.W * float4(sculpt_pos_paint.xyz, 1.0)).xyz;");
|
||||
}
|
||||
}
|
||||
}
|
||||
sculpt_make_paint_run(kong);
|
||||
|
||||
con_paint->data->shader_from_source = true;
|
||||
gpu_create_shaders_from_kong(node_shader_get(kong), &con_paint->data->vertex_shader, &con_paint->data->fragment_shader,
|
||||
|
||||
@@ -1,6 +1,85 @@
|
||||
|
||||
#include "../global.h"
|
||||
|
||||
static material_data_t *particle_bullet_material = NULL;
|
||||
|
||||
static node_shader_context_t *make_particle_bullet_run() {
|
||||
material_t *mat = GC_ALLOC_INIT(material_t, {.name = "particle_bullet", .canvas = NULL});
|
||||
shader_context_t *props = GC_ALLOC_INIT(shader_context_t, {
|
||||
.name = "mesh",
|
||||
.depth_write = true,
|
||||
.compare_mode = "less",
|
||||
.cull_mode = "clockwise",
|
||||
.vertex_elements = any_array_create_from_raw(
|
||||
(void *[]){
|
||||
GC_ALLOC_INIT(vertex_element_t, {.name = "pos", .data = "short4norm"}),
|
||||
GC_ALLOC_INIT(vertex_element_t, {.name = "nor", .data = "short2norm"}),
|
||||
GC_ALLOC_INIT(vertex_element_t, {.name = "tex", .data = "short2norm"}),
|
||||
},
|
||||
3),
|
||||
.color_attachments = any_array_create_from_raw((void *[]){"RGBA64", "RGBA64", "RGBA64"}, 3),
|
||||
.depth_attachment = "D32",
|
||||
});
|
||||
node_shader_context_t *con = node_shader_context_create(mat, props);
|
||||
node_shader_t *kong = node_shader_context_make_kong(con);
|
||||
|
||||
kong->frag_n = true;
|
||||
kong->frag_out = "float4[3]";
|
||||
|
||||
node_shader_add_constant(kong, "WVP: float4x4", "_world_view_proj_matrix");
|
||||
node_shader_write_vert(kong, "output.pos = constants.WVP * float4(input.pos.xyz, 1.0);");
|
||||
|
||||
node_shader_add_out(kong, "tex_coord: float2");
|
||||
node_shader_write_vert(kong, "output.tex_coord = input.tex;");
|
||||
|
||||
node_shader_add_function(kong, str_octahedron_wrap);
|
||||
node_shader_add_function(kong, str_pack_float_int16);
|
||||
|
||||
node_shader_write_frag(kong, "var basecol: float3 = float3(0.8, 0.8, 0.8);");
|
||||
node_shader_write_frag(kong, "var roughness: float = 0.5;");
|
||||
node_shader_write_frag(kong, "var metallic: float = 0.0;");
|
||||
node_shader_write_frag(kong, "var occlusion: float = 1.0;");
|
||||
node_shader_write_frag(kong, "n = n / (abs(n.x) + abs(n.y) + abs(n.z));");
|
||||
node_shader_write_frag(kong, "if (n.z < 0.0) { n.xy = octahedron_wrap(n.xy); }");
|
||||
node_shader_write_frag(kong, "output[0] = float4(n.xy, roughness, pack_f32_i16(metallic, uint(0)));");
|
||||
node_shader_write_frag(kong, "output[1] = float4(basecol, occlusion);");
|
||||
node_shader_write_frag(kong, "output[2] = float4(0.0, 0.0, input.tex_coord.xy);");
|
||||
|
||||
parser_material_finalize(con);
|
||||
con->data->shader_from_source = true;
|
||||
gpu_create_shaders_from_kong(node_shader_get(kong), &con->data->vertex_shader, &con->data->fragment_shader, &con->data->_->vertex_shader_size,
|
||||
&con->data->_->fragment_shader_size);
|
||||
return con;
|
||||
}
|
||||
|
||||
material_data_t *make_particle_get_bullet_material() {
|
||||
if (particle_bullet_material != NULL) {
|
||||
return particle_bullet_material;
|
||||
}
|
||||
|
||||
node_shader_context_t *con = make_particle_bullet_run();
|
||||
shader_context_load(con->data);
|
||||
|
||||
shader_data_t *sd = GC_ALLOC_INIT(shader_data_t, {
|
||||
.name = "particle_bullet",
|
||||
.contexts = any_array_create_from_raw((void *[]){con->data}, 1),
|
||||
});
|
||||
material_context_t *mcon = GC_ALLOC_INIT(material_context_t, {
|
||||
.name = "mesh",
|
||||
.bind_constants = any_array_create_from_raw((void *[]){}, 0),
|
||||
.bind_textures = any_array_create_from_raw((void *[]){}, 0),
|
||||
});
|
||||
material_context_load(mcon);
|
||||
particle_bullet_material = GC_ALLOC_INIT(material_data_t, {
|
||||
.name = "particle_bullet",
|
||||
.shader = "",
|
||||
.contexts = any_array_create_from_raw((void *[]){mcon}, 1),
|
||||
._ = GC_ALLOC_INIT(material_data_runtime_t, {.uid = 0.0, .shader = sd}),
|
||||
});
|
||||
gc_root(particle_bullet_material);
|
||||
return particle_bullet_material;
|
||||
}
|
||||
|
||||
void make_particle_mask(node_shader_t *kong) {
|
||||
node_shader_add_out(kong, "wpos: float4");
|
||||
node_shader_add_constant(kong, "W: float4x4", "_world_matrix");
|
||||
|
||||
+717
-149
File diff suppressed because it is too large
Load Diff
@@ -164,7 +164,9 @@ void render_path_paint_commands_particle(i32 tid, char *texpaint, bool is_mask)
|
||||
void render_path_paint_commands_paint(bool dilation) {
|
||||
i32 tid = g_context->layer->id;
|
||||
|
||||
if (g_context->layer->texpaint_sculpt != NULL) {
|
||||
bool picking_tool = g_context->tool == TOOL_TYPE_COLORID || g_context->tool == TOOL_TYPE_PICKER || g_context->tool == TOOL_TYPE_MATERIAL ||
|
||||
g_context->tool == TOOL_TYPE_CURSOR;
|
||||
if (g_context->layer->texpaint_sculpt != NULL && !picking_tool) {
|
||||
render_path_sculpt_commands();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -184,6 +184,16 @@ void slot_layer_swap(slot_layer_t *raw, slot_layer_t *other) {
|
||||
other->texpaint_preview = _texpaint_preview;
|
||||
}
|
||||
|
||||
if (raw->texpaint_sculpt != NULL && other->texpaint_sculpt != NULL) {
|
||||
render_target_t *srt0 = any_map_get(render_path_render_targets, string("texpaint_sculpt%s", raw->ext));
|
||||
render_target_t *srt1 = any_map_get(render_path_render_targets, string("texpaint_sculpt%s", other->ext));
|
||||
srt0->_image = other->texpaint_sculpt;
|
||||
srt1->_image = raw->texpaint_sculpt;
|
||||
gpu_texture_t *_texpaint_sculpt = raw->texpaint_sculpt;
|
||||
raw->texpaint_sculpt = other->texpaint_sculpt;
|
||||
other->texpaint_sculpt = _texpaint_sculpt;
|
||||
}
|
||||
|
||||
if (slot_layer_is_layer(raw) && slot_layer_is_layer(other)) {
|
||||
render_target_t *nor0 = any_map_get(render_path_render_targets, string("texpaint_nor%s", raw->ext));
|
||||
nor0->_image = other->texpaint_nor;
|
||||
@@ -441,6 +451,19 @@ void slot_layer_resize_and_set_bits(slot_layer_t *raw) {
|
||||
render_target_t *rt = any_map_get(rts, string("texpaint%s", raw->ext));
|
||||
rt->_image = raw->texpaint;
|
||||
}
|
||||
|
||||
// Clear and repack the base mesh
|
||||
if (raw->texpaint_sculpt != NULL) {
|
||||
gpu_texture_t *_texpaint_sculpt = raw->texpaint_sculpt;
|
||||
raw->texpaint_sculpt = gpu_create_render_target(res_x, res_y, GPU_TEXTURE_FORMAT_RGBA128);
|
||||
sculpt_import_mesh_pack_to_texture(raw->texpaint_sculpt);
|
||||
gpu_delete_texture(_texpaint_sculpt);
|
||||
|
||||
render_target_t *srt = any_map_get(rts, string("texpaint_sculpt%s", raw->ext));
|
||||
srt->width = res_x;
|
||||
srt->height = res_y;
|
||||
srt->_image = raw->texpaint_sculpt;
|
||||
}
|
||||
}
|
||||
|
||||
void slot_layer_to_fill_layer_on_next_frame(void *_) {
|
||||
|
||||
@@ -450,7 +450,7 @@ void tab_layers_draw_layer_slot_full(slot_layer_t *l, i32 i) {
|
||||
}
|
||||
|
||||
// Blending combo
|
||||
if (!slot_layer_is_group(l) && !slot_layer_is_mask(l) && !slot_layer_is_filter(l)) {
|
||||
if (!slot_layer_is_group(l) && !slot_layer_is_mask(l) && !slot_layer_is_filter(l) && l->texpaint_sculpt == NULL) {
|
||||
g_ui->_x = uix + uiw * 0.60;
|
||||
g_ui->_y = uiy;
|
||||
g_ui->_w = uiw * 0.30;
|
||||
@@ -460,7 +460,7 @@ void tab_layers_draw_layer_slot_full(slot_layer_t *l, i32 i) {
|
||||
// Object combo
|
||||
if (!slot_layer_is_group(l) && !slot_layer_is_mask(l) && !slot_layer_is_filter(l)) {
|
||||
g_ui->_x = uix + uiw * 0.60;
|
||||
g_ui->_y = uiy + center * 2;
|
||||
g_ui->_y = l->texpaint_sculpt != NULL ? uiy + center : uiy + center * 2;
|
||||
g_ui->_w = uiw * 0.30;
|
||||
tab_layers_combo_object(l, false);
|
||||
}
|
||||
@@ -632,7 +632,7 @@ void tab_layers_draw_layer_context_menu_draw() {
|
||||
ui_menu_keep_open = true;
|
||||
}
|
||||
|
||||
if (!slot_layer_is_group(l) && !slot_layer_is_mask(l) && !slot_layer_is_filter(l)) {
|
||||
if (!slot_layer_is_group(l) && !slot_layer_is_mask(l) && !slot_layer_is_filter(l) && l->texpaint_sculpt == NULL) {
|
||||
if (tab_layers_combo_blending(l, true)->changed) {
|
||||
ui_menu_keep_open = true;
|
||||
}
|
||||
@@ -915,7 +915,7 @@ void tab_layers_draw_layer_slot(slot_layer_t *l, i32 i, bool mini) {
|
||||
}
|
||||
|
||||
bool is_sculpt_layer = l->texpaint_sculpt != NULL;
|
||||
if (g_config->workflow == WORKFLOW_SCULPT && !is_sculpt_layer) {
|
||||
if (g_config->workflow == WORKFLOW_SCULPT && !is_sculpt_layer && !slot_layer_is_group(l) && !slot_layer_is_mask(l)) {
|
||||
return;
|
||||
}
|
||||
if (g_config->workflow != WORKFLOW_SCULPT && is_sculpt_layer) {
|
||||
|
||||
@@ -812,12 +812,9 @@ void ui_menubar_draw_category_items() {
|
||||
(void *[]){
|
||||
tr("PBR"),
|
||||
tr("Base"),
|
||||
tr("Sculpt"),
|
||||
},
|
||||
2);
|
||||
|
||||
if (g_config->experimental) {
|
||||
any_array_push(workflow_items, tr("Sculpt"));
|
||||
}
|
||||
3);
|
||||
|
||||
g_config->workflow = ui_inline_radio(workflow_handle, workflow_items, UI_ALIGN_LEFT);
|
||||
if (workflow_handle->changed) {
|
||||
|
||||
@@ -85,7 +85,7 @@ void ui_view2d_draw_edit() {
|
||||
h_view2d_grid_snap->b = g_config->view2d_grid_snap;
|
||||
g_config->view2d_grid_snap = ui_check(h_view2d_grid_snap, tr("Grid Snap"), any_map_get(g_keymap, "grid_snap"));
|
||||
if (h_view2d_grid_snap->changed) {
|
||||
ui_menu_keep_open = true;
|
||||
ui_menu_keep_open = true;
|
||||
}
|
||||
|
||||
ui_menu_separator();
|
||||
|
||||
@@ -5,6 +5,9 @@ i32 uniforms_ext_i32_link(object_t *object, material_data_t *mat, char *link) {
|
||||
if (string_equals(link, "_bloom_current_mip")) {
|
||||
return render_path_base_bloom_current_mip;
|
||||
}
|
||||
else if (string_equals(link, "_sculpt_vertex_offset")) {
|
||||
return sculpt_object_vertex_offset(object->ext);
|
||||
}
|
||||
return INT_MAX;
|
||||
}
|
||||
|
||||
@@ -72,6 +75,9 @@ f32 uniforms_ext_f32_link(object_t *object, material_data_t *mat, char *link) {
|
||||
val *= pen_pressure * g_config->pressure_sensitivity;
|
||||
}
|
||||
val *= val;
|
||||
if (g_config->workflow == WORKFLOW_SCULPT) {
|
||||
val *= 0.8;
|
||||
}
|
||||
return val;
|
||||
}
|
||||
else if (string_equals(link, "_brush_scale")) {
|
||||
@@ -88,6 +94,20 @@ f32 uniforms_ext_f32_link(object_t *object, material_data_t *mat, char *link) {
|
||||
else if (string_equals(link, "_object_id")) {
|
||||
return array_index_of(g_project->_->paint_objects, object->ext);
|
||||
}
|
||||
else if (string_equals(link, "_sculpt_mask_offset")) {
|
||||
i32 om = slot_layer_get_object_mask(g_context->layer);
|
||||
if (om <= 0 || om > g_project->_->paint_objects->length) {
|
||||
return 0;
|
||||
}
|
||||
return sculpt_object_vertex_offset(g_project->_->paint_objects->buffer[om - 1]);
|
||||
}
|
||||
else if (string_equals(link, "_sculpt_mask_count")) {
|
||||
i32 om = slot_layer_get_object_mask(g_context->layer);
|
||||
if (om <= 0 || om > g_project->_->paint_objects->length) {
|
||||
return config_get_texture_res_x() * config_get_texture_res_y();
|
||||
}
|
||||
return g_project->_->paint_objects->buffer[om - 1]->data->index_array->length;
|
||||
}
|
||||
else if (string_equals(link, "_dilate_radius")) {
|
||||
return util_uv_dilatemap != NULL ? g_config->dilate_radius : 0.0;
|
||||
}
|
||||
@@ -289,9 +309,10 @@ vec4_t uniforms_ext_vec4_link(object_t *object, material_data_t *mat, char *link
|
||||
mat4_t uniforms_ext_mat4_link(object_t *object, material_data_t *mat, char *link) {
|
||||
if (string_equals(link, "_decal_layer_matrix")) { // Decal layer
|
||||
mat4_t m = mat4_inv(g_context->layer->decal_mat);
|
||||
f32 f = object->parent->transform->scale.x * object->transform->scale_world;
|
||||
m = mat4_scale(m, (vec4_t){f, f, f, 1.0});
|
||||
m = mat4_mult_mat(m, uniforms_ext_ortho_p);
|
||||
f32 parent_scale = object->parent != NULL ? object->parent->transform->scale.x : 1.0;
|
||||
f32 f = parent_scale * object->transform->scale_world;
|
||||
m = mat4_scale(m, (vec4_t){f, f, f, 1.0});
|
||||
m = mat4_mult_mat(m, uniforms_ext_ortho_p);
|
||||
return m;
|
||||
}
|
||||
|
||||
@@ -327,8 +348,8 @@ gpu_texture_t *uniforms_ext_tex_link(object_t *object, material_data_t *mat, cha
|
||||
return rt->_image;
|
||||
}
|
||||
else if (string_equals(link, "_texpaint_sculpt_undo")) {
|
||||
i32 i = history_undo_i - 1 < 0 ? g_config->undo_steps - 1 : history_undo_i - 1;
|
||||
render_target_t *rt = any_map_get(render_path_render_targets, string("texpaint_sculpt_undo%d", i));
|
||||
// Per-frame accumulation reference
|
||||
render_target_t *rt = any_map_get(render_path_render_targets, "texpaint_sculpt_ref");
|
||||
return rt->_image;
|
||||
}
|
||||
else if (string_equals(link, "_texcolorid")) {
|
||||
@@ -380,8 +401,13 @@ gpu_texture_t *uniforms_ext_tex_link(object_t *object, material_data_t *mat, cha
|
||||
return rt->_image;
|
||||
}
|
||||
if (starts_with(link, "_texpaint_vert")) {
|
||||
i32 tid = parse_int(substring(link, string_length(link) - 1, string_length(link)));
|
||||
return tid < g_project->_->layers->length ? g_project->_->layers->buffer[tid]->texpaint : NULL;
|
||||
i32 tid = parse_int(substring(link, string_length("_texpaint_vert"), string_length(link)));
|
||||
for (i32 i = 0; i < g_project->_->layers->length; ++i) {
|
||||
if (g_project->_->layers->buffer[i]->id == tid) {
|
||||
return g_project->_->layers->buffer[i]->texpaint;
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
if (starts_with(link, "_texpaint_nor")) {
|
||||
i32 tid = parse_int(substring(link, string_length(link) - 1, string_length(link)));
|
||||
|
||||
@@ -115,6 +115,23 @@ void layers_resize() {
|
||||
if (render_path_paint_live_layer != NULL) {
|
||||
slot_layer_resize_and_set_bits(render_path_paint_live_layer);
|
||||
}
|
||||
|
||||
render_target_t *sculpt_ref = any_map_get(rts, "texpaint_sculpt_ref");
|
||||
if (sculpt_ref != NULL) {
|
||||
gpu_delete_texture(sculpt_ref->_image);
|
||||
sculpt_ref->width = config_get_texture_res_x();
|
||||
sculpt_ref->height = config_get_texture_res_y();
|
||||
sculpt_ref->_image = gpu_create_render_target(config_get_texture_res_x(), config_get_texture_res_y(), GPU_TEXTURE_FORMAT_RGBA128);
|
||||
}
|
||||
|
||||
render_target_t *sculpt_base = any_map_get(rts, "texpaint_sculpt_base");
|
||||
if (sculpt_base != NULL) {
|
||||
gpu_delete_texture(sculpt_base->_image);
|
||||
sculpt_base->width = config_get_texture_res_x();
|
||||
sculpt_base->height = config_get_texture_res_y();
|
||||
sculpt_base->_image = gpu_create_render_target(config_get_texture_res_x(), config_get_texture_res_y(), GPU_TEXTURE_FORMAT_RGBA128);
|
||||
}
|
||||
|
||||
render_path_raytrace_ready = false; // Rebuild baketex
|
||||
g_context->ddirty = 2;
|
||||
}
|
||||
@@ -344,7 +361,7 @@ void layers_update_fill_layers() {
|
||||
if (l->texpaint_sculpt != NULL) {
|
||||
i32 tid = l->id;
|
||||
i32 hid = history_undo_i - 1 < 0 ? g_config->undo_steps - 1 : history_undo_i - 1;
|
||||
sculpt_import_mesh_pack_to_texture(g_context->paint_object->data, l->texpaint_sculpt);
|
||||
sculpt_import_mesh_pack_to_texture(l->texpaint_sculpt);
|
||||
render_path_set_target(string("texpaint_sculpt_undo%d", hid), NULL, NULL, GPU_CLEAR_NONE, 0, 0.0);
|
||||
render_path_bind_target(string("texpaint_sculpt%d", tid), "tex");
|
||||
render_path_draw_shader("Scene/copy_pass/copyRGBA128_pass");
|
||||
@@ -424,7 +441,7 @@ void layers_update_fill_layer(bool parse_paint) {
|
||||
if (g_context->layer->texpaint_sculpt != NULL) {
|
||||
i32 tid = g_context->layer->id;
|
||||
i32 hid = history_undo_i - 1 < 0 ? g_config->undo_steps - 1 : history_undo_i - 1;
|
||||
sculpt_import_mesh_pack_to_texture(g_context->paint_object->data, g_context->layer->texpaint_sculpt);
|
||||
sculpt_import_mesh_pack_to_texture(g_context->layer->texpaint_sculpt);
|
||||
render_path_set_target(string("texpaint_sculpt_undo%d", hid), NULL, NULL, GPU_CLEAR_NONE, 0, 0.0);
|
||||
render_path_bind_target(string("texpaint_sculpt%d", tid), "tex");
|
||||
render_path_draw_shader("Scene/copy_pass/copyRGBA128_pass");
|
||||
@@ -637,6 +654,13 @@ slot_layer_t *layers_new_group() {
|
||||
return l;
|
||||
}
|
||||
|
||||
static slot_layer_t *_layers_path_sculpt_layer = NULL;
|
||||
|
||||
void layers_new_path_layer_sculpt_init(void *_) {
|
||||
sculpt_init();
|
||||
sculpt_init_sculpt_texture(_layers_path_sculpt_layer);
|
||||
}
|
||||
|
||||
slot_layer_t *layers_new_path_layer(bool curved) {
|
||||
slot_layer_t *l = layers_new_layer(true, -1, NULL);
|
||||
if (l == NULL) {
|
||||
@@ -650,6 +674,12 @@ slot_layer_t *layers_new_path_layer(bool curved) {
|
||||
l->path_curved = curved;
|
||||
l->path_material = g_context->material;
|
||||
l->name = string(curved ? "Curve %d" : "Path %d", l->id + 1);
|
||||
|
||||
if (g_config->workflow == WORKFLOW_SCULPT) {
|
||||
_layers_path_sculpt_layer = l;
|
||||
sys_notify_on_next_frame(&layers_new_path_layer_sculpt_init, NULL);
|
||||
}
|
||||
|
||||
return l;
|
||||
}
|
||||
|
||||
@@ -663,9 +693,8 @@ void layers_create_fill_layer_on_next_frame(void *_) {
|
||||
l->object_mask = g_context->layer_filter;
|
||||
|
||||
if (g_config->workflow == WORKFLOW_SCULPT) {
|
||||
mesh_data_t *md = g_context->paint_object->data;
|
||||
sculpt_init();
|
||||
sculpt_init_sculpt_texture(l, md);
|
||||
sculpt_init_sculpt_texture(l);
|
||||
}
|
||||
|
||||
history_to_fill_layer();
|
||||
|
||||
@@ -27,6 +27,7 @@ void util_particle_update() {
|
||||
}
|
||||
|
||||
util_particle_init_physics();
|
||||
make_particle_get_bullet_material();
|
||||
physics_world_t *world = physics_world_active;
|
||||
physics_world_update(world);
|
||||
|
||||
@@ -73,6 +74,7 @@ void util_particle_update() {
|
||||
mesh_object_t *mo = o->ext;
|
||||
mo->base->name = ".Bullet";
|
||||
mo->base->visible = true;
|
||||
mo->material = make_particle_get_bullet_material();
|
||||
|
||||
util_render_pick_pos_nor_tex();
|
||||
f32 nx = g_context->norx_picked;
|
||||
|
||||
@@ -77,6 +77,9 @@ static void path_set_camera(f32_array_t *points_camera, i32 num_camera, i32 ci)
|
||||
camera_object_build_proj(scene_camera, points_camera->buffer[ci * 9 + 8]);
|
||||
camera_object_build_mat(scene_camera);
|
||||
render_path_base_draw_gbuffer();
|
||||
if (g_context->layer->texpaint_sculpt != NULL) {
|
||||
render_path_sculpt_snapshot_gbuffer();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -291,6 +294,11 @@ static void path_repaint(slot_layer_t *l) {
|
||||
|
||||
slot_layer_clear(l, 0x00000000, NULL, 1.0, layers_default_rough, 0.0);
|
||||
|
||||
if (l->texpaint_sculpt != NULL) {
|
||||
// Restore the undeformed base mesh
|
||||
sculpt_import_mesh_pack_to_texture(l->texpaint_sculpt);
|
||||
}
|
||||
|
||||
vec4_t _camera_loc = scene_camera->base->transform->loc;
|
||||
quat_t _camera_rot = scene_camera->base->transform->rot;
|
||||
|
||||
|
||||
@@ -226,6 +226,10 @@ void util_render_make_brush_preview() {
|
||||
return;
|
||||
}
|
||||
|
||||
if (g_config->workflow == WORKFLOW_SCULPT) {
|
||||
return;
|
||||
}
|
||||
|
||||
gpu_texture_t *current = _draw_current;
|
||||
bool in_use = gpu_in_use;
|
||||
if (in_use)
|
||||
|
||||
Reference in New Issue
Block a user