Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAntonio Vazquez <blendergit@gmail.com>2022-06-16 17:27:57 +0300
committerPhilipp Oeser <info@graphics-engineer.com>2022-06-22 13:19:09 +0300
commitde267abe4eb8d761e56f62c97ee588a1d6fdbd3f (patch)
tree32bf6d46a00cadf5ebedc74ca5b4917f724e43e2
parent2c357c226870c57ec381bc64942e1e4b6355db1f (diff)
Fix T98904: GPencil sculpt brushes break after you delete a brush
There were two problems here: 1) Console warnings due to brush was None. 2) It was impossible to recreate a brush. This patch fixes both issues and it is now possible to recreate any brush. Differential Revision: https://developer.blender.org/D15213 Reviewed by: @dflelinto
-rw-r--r--release/scripts/startup/bl_ui/properties_paint_common.py2
-rw-r--r--release/scripts/startup/bl_ui/space_view3d.py11
-rw-r--r--source/blender/editors/sculpt_paint/paint_ops.c148
3 files changed, 147 insertions, 14 deletions
diff --git a/release/scripts/startup/bl_ui/properties_paint_common.py b/release/scripts/startup/bl_ui/properties_paint_common.py
index 320b5f60911..e0c5da5ee1a 100644
--- a/release/scripts/startup/bl_ui/properties_paint_common.py
+++ b/release/scripts/startup/bl_ui/properties_paint_common.py
@@ -1295,6 +1295,8 @@ def brush_basic_gpencil_paint_settings(layout, context, brush, *, compact=False)
def brush_basic_gpencil_sculpt_settings(layout, _context, brush, *, compact=False):
+ if brush is None:
+ return
gp_settings = brush.gpencil_settings
if gp_settings is None:
return
diff --git a/release/scripts/startup/bl_ui/space_view3d.py b/release/scripts/startup/bl_ui/space_view3d.py
index a8624030564..625ba6016c6 100644
--- a/release/scripts/startup/bl_ui/space_view3d.py
+++ b/release/scripts/startup/bl_ui/space_view3d.py
@@ -97,7 +97,7 @@ class VIEW3D_HT_tool_header(Header):
elif tool_mode == 'PAINT_GPENCIL':
if is_valid_context:
brush = context.tool_settings.gpencil_paint.brush
- if brush.gpencil_tool != 'ERASE':
+ if brush and brush.gpencil_tool != 'ERASE':
if brush.gpencil_tool != 'TINT':
layout.popover("VIEW3D_PT_tools_grease_pencil_brush_advanced")
@@ -108,10 +108,11 @@ class VIEW3D_HT_tool_header(Header):
elif tool_mode == 'SCULPT_GPENCIL':
if is_valid_context:
brush = context.tool_settings.gpencil_sculpt_paint.brush
- tool = brush.gpencil_sculpt_tool
- if tool in {'SMOOTH', 'RANDOMIZE'}:
- layout.popover("VIEW3D_PT_tools_grease_pencil_sculpt_options")
- layout.popover("VIEW3D_PT_tools_grease_pencil_sculpt_appearance")
+ if brush:
+ tool = brush.gpencil_sculpt_tool
+ if tool in {'SMOOTH', 'RANDOMIZE'}:
+ layout.popover("VIEW3D_PT_tools_grease_pencil_sculpt_options")
+ layout.popover("VIEW3D_PT_tools_grease_pencil_sculpt_appearance")
elif tool_mode == 'WEIGHT_GPENCIL':
if is_valid_context:
layout.popover("VIEW3D_PT_tools_grease_pencil_weight_appearance")
diff --git a/source/blender/editors/sculpt_paint/paint_ops.c b/source/blender/editors/sculpt_paint/paint_ops.c
index 926a564184a..0f2b02ed3ab 100644
--- a/source/blender/editors/sculpt_paint/paint_ops.c
+++ b/source/blender/editors/sculpt_paint/paint_ops.c
@@ -82,11 +82,86 @@ static void BRUSH_OT_add(wmOperatorType *ot)
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
}
+static eGPBrush_Presets gpencil_get_brush_preset_from_tool(bToolRef *tool,
+ enum eContextObjectMode mode)
+{
+ switch (mode) {
+ case CTX_MODE_PAINT_GPENCIL: {
+ if (STREQ(tool->runtime->data_block, "DRAW")) {
+ return GP_BRUSH_PRESET_PENCIL;
+ }
+ else if (STREQ(tool->runtime->data_block, "FILL")) {
+ return GP_BRUSH_PRESET_FILL_AREA;
+ }
+ else if (STREQ(tool->runtime->data_block, "ERASE")) {
+ return GP_BRUSH_PRESET_ERASER_SOFT;
+ }
+ else if (STREQ(tool->runtime->data_block, "TINT")) {
+ return GP_BRUSH_PRESET_TINT;
+ }
+ break;
+ }
+ case CTX_MODE_SCULPT_GPENCIL: {
+ if (STREQ(tool->runtime->data_block, "SMOOTH")) {
+ return GP_BRUSH_PRESET_SMOOTH_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "STRENGTH")) {
+ return GP_BRUSH_PRESET_STRENGTH_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "THICKNESS")) {
+ return GP_BRUSH_PRESET_THICKNESS_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "GRAB")) {
+ return GP_BRUSH_PRESET_GRAB_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "PUSH")) {
+ return GP_BRUSH_PRESET_PUSH_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "TWIST")) {
+ return GP_BRUSH_PRESET_TWIST_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "PINCH")) {
+ return GP_BRUSH_PRESET_PINCH_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "RANDOMIZE")) {
+ return GP_BRUSH_PRESET_RANDOMIZE_STROKE;
+ }
+ else if (STREQ(tool->runtime->data_block, "CLONE")) {
+ return GP_BRUSH_PRESET_CLONE_STROKE;
+ }
+ break;
+ }
+ case CTX_MODE_WEIGHT_GPENCIL: {
+ return GP_BRUSH_PRESET_DRAW_WEIGHT;
+ }
+ case CTX_MODE_VERTEX_GPENCIL: {
+ if (STREQ(tool->runtime->data_block, "DRAW")) {
+ return GP_BRUSH_PRESET_VERTEX_DRAW;
+ }
+ else if (STREQ(tool->runtime->data_block, "BLUR")) {
+ return GP_BRUSH_PRESET_VERTEX_BLUR;
+ }
+ else if (STREQ(tool->runtime->data_block, "AVERAGE")) {
+ return GP_BRUSH_PRESET_VERTEX_AVERAGE;
+ }
+ else if (STREQ(tool->runtime->data_block, "SMEAR")) {
+ return GP_BRUSH_PRESET_VERTEX_SMEAR;
+ }
+ else if (STREQ(tool->runtime->data_block, "REPLACE")) {
+ return GP_BRUSH_PRESET_VERTEX_REPLACE;
+ }
+ break;
+ }
+ default:
+ return GP_BRUSH_PRESET_UNKNOWN;
+ break;
+ }
+ return GP_BRUSH_PRESET_UNKNOWN;
+}
+
static int brush_add_gpencil_exec(bContext *C, wmOperator *UNUSED(op))
{
- // int type = RNA_enum_get(op->ptr, "type");
- ToolSettings *ts = CTX_data_tool_settings(C);
- Paint *paint = &ts->gp_paint->paint;
+ Paint *paint = BKE_paint_get_active_from_context(C);
Brush *br = BKE_paint_brush(paint);
Main *bmain = CTX_data_main(C);
@@ -94,15 +169,70 @@ static int brush_add_gpencil_exec(bContext *C, wmOperator *UNUSED(op))
br = (Brush *)BKE_id_copy(bmain, &br->id);
}
else {
- br = BKE_brush_add(bmain, "Brush", OB_MODE_PAINT_GPENCIL);
+ /* Get the active tool to determine what type of brush is active. */
+ bScreen *screen = CTX_wm_screen(C);
+ if (screen == NULL) {
+ return OPERATOR_CANCELLED;
+ }
- /* Init grease pencil specific data. */
- BKE_brush_init_gpencil_settings(br);
- }
+ bToolRef *tool = NULL;
+ LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
+ if (area->spacetype == SPACE_VIEW3D) {
+ /* Check the current tool is a brush. */
+ bToolRef *tref = area->runtime.tool;
+ if (tref && tref->runtime && tref->runtime->data_block[0]) {
+ tool = tref;
+ break;
+ }
+ }
+ }
- id_us_min(&br->id); /* fake user only */
+ if (tool == NULL) {
+ return OPERATOR_CANCELLED;
+ }
- BKE_paint_brush_set(paint, br);
+ /* Get Brush mode base on context mode. */
+ const enum eContextObjectMode mode = CTX_data_mode_enum(C);
+ eObjectMode obmode = OB_MODE_PAINT_GPENCIL;
+ switch (mode) {
+ case CTX_MODE_PAINT_GPENCIL:
+ obmode = OB_MODE_PAINT_GPENCIL;
+ break;
+ case CTX_MODE_SCULPT_GPENCIL:
+ obmode = OB_MODE_SCULPT_GPENCIL;
+ break;
+ case CTX_MODE_WEIGHT_GPENCIL:
+ obmode = OB_MODE_WEIGHT_GPENCIL;
+ break;
+ case CTX_MODE_VERTEX_GPENCIL:
+ obmode = OB_MODE_VERTEX_GPENCIL;
+ break;
+ default:
+ return OPERATOR_CANCELLED;
+ break;
+ }
+
+ /* Get brush preset using the actual tool. */
+ eGPBrush_Presets preset = gpencil_get_brush_preset_from_tool(tool, mode);
+
+ /* Capitalize Brush name first letter using the tool name. */
+ char name[64];
+ BLI_strncpy(name, tool->runtime->data_block, sizeof(name));
+ BLI_str_tolower_ascii(name, sizeof(name));
+ name[0] = BLI_toupper_ascii(name[0]);
+
+ /* Create the brush and assign default values. */
+ br = BKE_brush_add(bmain, name, obmode);
+ if (br) {
+ BKE_brush_init_gpencil_settings(br);
+ BKE_gpencil_brush_preset_set(bmain, br, preset);
+ }
+ }
+
+ if (br) {
+ id_us_min(&br->id); /* fake user only */
+ BKE_paint_brush_set(paint, br);
+ }
return OPERATOR_FINISHED;
}