diff options
-rw-r--r-- | release/scripts/startup/bl_ui/space_view3d_toolbar.py | 2 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/material.c | 2 | ||||
-rw-r--r-- | source/blender/draw/modes/paint_texture_mode.c | 12 | ||||
-rw-r--r-- | source/blender/draw/modes/shaders/paint_texture_frag.glsl | 8 | ||||
-rw-r--r-- | source/blender/makesdna/DNA_material_types.h | 3 | ||||
-rw-r--r-- | source/blender/makesdna/DNA_scene_types.h | 9 | ||||
-rw-r--r-- | source/blender/makesrna/intern/rna_sculpt_paint.c | 15 |
7 files changed, 45 insertions, 6 deletions
diff --git a/release/scripts/startup/bl_ui/space_view3d_toolbar.py b/release/scripts/startup/bl_ui/space_view3d_toolbar.py index 302360386d5..95f97ee454f 100644 --- a/release/scripts/startup/bl_ui/space_view3d_toolbar.py +++ b/release/scripts/startup/bl_ui/space_view3d_toolbar.py @@ -511,6 +511,8 @@ class VIEW3D_PT_slots_projectpaint(View3DPanel, Panel): layout.menu("VIEW3D_MT_tools_projectpaint_uvlayer", text=uv_text, translate=False) have_image = settings.canvas is not None + layout.prop(settings, "interpolation", text="") + if settings.missing_uvs: layout.separator() split = layout.split() diff --git a/source/blender/blenkernel/intern/material.c b/source/blender/blenkernel/intern/material.c index 7e59d31571b..913bc9c47e6 100644 --- a/source/blender/blenkernel/intern/material.c +++ b/source/blender/blenkernel/intern/material.c @@ -1063,7 +1063,9 @@ static void fill_texpaint_slots_recursive(bNodeTree *nodetree, bNode *active_nod if (active_node == node) { ma->paint_active_slot = *index; } + ma->texpaintslot[*index].ima = (Image *)node->id; + ma->texpaintslot[*index].interp = ((NodeTexImage *)node->storage)->interpolation; /* for new renderer, we need to traverse the treeback in search of a UV node */ bNode *uvnode = nodetree_uv_node_recursive(node); diff --git a/source/blender/draw/modes/paint_texture_mode.c b/source/blender/draw/modes/paint_texture_mode.c index 200daf66c83..757b43b6c04 100644 --- a/source/blender/draw/modes/paint_texture_mode.c +++ b/source/blender/draw/modes/paint_texture_mode.c @@ -28,6 +28,8 @@ #include "BIF_gl.h" +#include "BKE_node.h" + /* If builtin shaders are needed */ #include "GPU_shader.h" #include "GPU_texture.h" @@ -139,8 +141,6 @@ static void PAINT_TEXTURE_engine_init(void *UNUSED(vedata)) if (!e_data.fallback_sh) { e_data.fallback_sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_UNIFORM_COLOR); - e_data.image_sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_UNIFORM_COLOR); - e_data.image_sh = DRW_shader_create_with_lib( datatoc_paint_texture_vert_glsl, NULL, datatoc_paint_texture_frag_glsl, @@ -189,7 +189,8 @@ static void PAINT_TEXTURE_cache_init(void *vedata) Object *ob = draw_ctx->obact; if (ob && ob->type == OB_MESH) { Scene *scene = draw_ctx->scene; - const bool use_material_slots = (scene->toolsettings->imapaint.mode == IMAGEPAINT_MODE_MATERIAL); + const ImagePaintSettings *imapaint = &scene->toolsettings->imapaint; + const bool use_material_slots = (imapaint->mode == IMAGEPAINT_MODE_MATERIAL); const Mesh *me = ob->data; const int mat_nr = max_ii(1, me->totcol); @@ -200,6 +201,7 @@ static void PAINT_TEXTURE_cache_init(void *vedata) for (int i = 0; i < mat_nr; i++) { Material *ma = give_current_material(ob, i + 1); Image *ima = (ma && ma->texpaintslot) ? ma->texpaintslot[ma->paint_active_slot].ima : NULL; + int interp = (ma && ma->texpaintslot) ? ma->texpaintslot[ma->paint_active_slot].interp : 0; GPUTexture *tex = ima ? GPU_texture_from_blender(ima, NULL, GL_TEXTURE_2D, false, 0.0f) : NULL; @@ -208,6 +210,7 @@ static void PAINT_TEXTURE_cache_init(void *vedata) DRW_shgroup_uniform_texture(grp, "image", tex); DRW_shgroup_uniform_float(grp, "alpha", &draw_ctx->v3d->overlay.texture_paint_mode_opacity, 1); DRW_shgroup_uniform_block(grp, "globalsBlock", globals_ubo); + DRW_shgroup_uniform_bool_copy(grp, "nearestInterp", interp == SHD_INTERP_CLOSEST); stl->g_data->shgroup_image_array[i] = grp; } else { @@ -216,7 +219,7 @@ static void PAINT_TEXTURE_cache_init(void *vedata) } } else { - Image *ima = scene->toolsettings->imapaint.canvas; + Image *ima = imapaint->canvas; GPUTexture *tex = ima ? GPU_texture_from_blender(ima, NULL, GL_TEXTURE_2D, false, 0.0f) : NULL; @@ -225,6 +228,7 @@ static void PAINT_TEXTURE_cache_init(void *vedata) DRW_shgroup_uniform_texture(grp, "image", tex); DRW_shgroup_uniform_float(grp, "alpha", &draw_ctx->v3d->overlay.texture_paint_mode_opacity, 1); DRW_shgroup_uniform_block(grp, "globalsBlock", globals_ubo); + DRW_shgroup_uniform_bool_copy(grp, "nearestInterp", imapaint->interp == IMAGEPAINT_INTERP_CLOSEST); stl->g_data->shgroup_image_array[0] = grp; } else { diff --git a/source/blender/draw/modes/shaders/paint_texture_frag.glsl b/source/blender/draw/modes/shaders/paint_texture_frag.glsl index 4305e20ce7b..68fd1be0886 100644 --- a/source/blender/draw/modes/shaders/paint_texture_frag.glsl +++ b/source/blender/draw/modes/shaders/paint_texture_frag.glsl @@ -4,8 +4,14 @@ out vec4 fragColor; uniform sampler2D image; uniform float alpha = 1.0; +uniform bool nearestInterp; void main() { - fragColor = vec4(texture(image, uv_interp).rgb, alpha); + vec2 uv = uv_interp; + if (nearestInterp) { + vec2 tex_size = vec2(textureSize(image, 0).xy); + uv = (floor(uv_interp * tex_size) + 0.5) / tex_size; + } + fragColor = vec4(texture(image, uv).rgb, alpha); } diff --git a/source/blender/makesdna/DNA_material_types.h b/source/blender/makesdna/DNA_material_types.h index 1e8173fc16d..6cd964fddf9 100644 --- a/source/blender/makesdna/DNA_material_types.h +++ b/source/blender/makesdna/DNA_material_types.h @@ -54,7 +54,8 @@ typedef struct TexPaintSlot { char *uvname; /** Do we have a valid image and UV map. */ int valid; - int pad; + /** Copy of node inteporlation setting. */ + int interp; } TexPaintSlot; typedef struct MaterialGPencilStyle { diff --git a/source/blender/makesdna/DNA_scene_types.h b/source/blender/makesdna/DNA_scene_types.h index a1e2afaf055..3186e8a435b 100644 --- a/source/blender/makesdna/DNA_scene_types.h +++ b/source/blender/makesdna/DNA_scene_types.h @@ -923,6 +923,9 @@ typedef struct ImagePaintSettings { float stencil_col[3]; /** Dither amount used when painting on byte images. */ float dither; + /** Display texture interpolation method. */ + int interp; + int pad; } ImagePaintSettings; /* ------------------------------------------- */ @@ -2207,6 +2210,12 @@ typedef enum eImagePaintMode { IMAGEPAINT_MODE_IMAGE, /* select texture paint image directly */ } eImagePaintMode; +/* ImagePaintSettings.interp */ +enum { + IMAGEPAINT_INTERP_LINEAR = 0, + IMAGEPAINT_INTERP_CLOSEST, +}; + /* ImagePaintSettings.flag */ #define IMAGEPAINT_DRAWING (1 << 0) // #define IMAGEPAINT_DRAW_TOOL (1 << 1) // deprecated diff --git a/source/blender/makesrna/intern/rna_sculpt_paint.c b/source/blender/makesrna/intern/rna_sculpt_paint.c index 581b0e94aad..f9f21c4c76a 100644 --- a/source/blender/makesrna/intern/rna_sculpt_paint.c +++ b/source/blender/makesrna/intern/rna_sculpt_paint.c @@ -872,6 +872,14 @@ static void rna_def_image_paint(BlenderRNA *brna) {0, NULL, 0, NULL, NULL} }; + static const EnumPropertyItem paint_interp_items[] = { + {IMAGEPAINT_INTERP_LINEAR, "LINEAR", 0, + "Linear", "Linear interpolation"}, + {IMAGEPAINT_INTERP_CLOSEST, "CLOSEST", 0, + "Closest", "No interpolation (sample closest texel)"}, + {0, NULL, 0, NULL, NULL} + }; + srna = RNA_def_struct(brna, "ImagePaint", "Paint"); RNA_def_struct_sdna(srna, "ImagePaintSettings"); RNA_def_struct_path_func(srna, "rna_ImagePaintSettings_path"); @@ -964,6 +972,13 @@ static void rna_def_image_paint(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Mode", "Mode of operation for projection painting"); RNA_def_property_update(prop, NC_SCENE | ND_TOOLSETTINGS, "rna_ImaPaint_mode_update"); + prop = RNA_def_property(srna, "interpolation", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "interp"); + RNA_def_property_flag(prop, PROP_CONTEXT_UPDATE); + RNA_def_property_enum_items(prop, paint_interp_items); + RNA_def_property_ui_text(prop, "Interpolation", "Texture filtering type"); + RNA_def_property_update(prop, NC_SCENE | ND_TOOLSETTINGS, "rna_ImaPaint_mode_update"); + /* Missing data */ prop = RNA_def_property(srna, "missing_uvs", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "missing_data", IMAGEPAINT_MISSING_UVS); |