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:
authorAntony Riakiotakis <kalast@gmail.com>2013-04-23 04:06:22 +0400
committerAntony Riakiotakis <kalast@gmail.com>2013-04-23 04:06:22 +0400
commit157244b13cf61d5889f5714167c6e5468ae35b15 (patch)
treee59778ab61ab8bf8823d245e96ed99885ed5729b /source/blender
parent0d14a1414c1c36f0e887c11de137f8b32a788852 (diff)
Add stencil control for mask overlay. Key combinations are the same as
regular stencil but use Alt as well, so Alt-Rclick is translation, Alt- clamping to avoid scaling of stencil to zero.
Diffstat (limited to 'source/blender')
-rw-r--r--source/blender/blenkernel/intern/brush.c10
-rw-r--r--source/blender/blenloader/intern/readfile.c6
-rw-r--r--source/blender/editors/sculpt_paint/paint_cursor.c22
-rw-r--r--source/blender/editors/sculpt_paint/paint_ops.c132
-rw-r--r--source/blender/makesdna/DNA_brush_types.h3
-rw-r--r--source/blender/makesrna/intern/rna_brush.c12
6 files changed, 143 insertions, 42 deletions
diff --git a/source/blender/blenkernel/intern/brush.c b/source/blender/blenkernel/intern/brush.c
index 064e902f831..e52d1d3b683 100644
--- a/source/blender/blenkernel/intern/brush.c
+++ b/source/blender/blenkernel/intern/brush.c
@@ -661,8 +661,8 @@ float BKE_brush_sample_masktex(const Scene *scene, Brush *br,
float x = 0.0f, y = 0.0f; /* Quite warnings */
float co[3];
- x = point_2d[0] - br->stencil_pos[0];
- y = point_2d[1] - br->stencil_pos[1];
+ x = point_2d[0] - br->mask_stencil_pos[0];
+ y = point_2d[1] - br->mask_stencil_pos[1];
if (rotation > 0.001f || rotation < -0.001f) {
const float angle = atan2f(y, x) + rotation;
@@ -672,12 +672,12 @@ float BKE_brush_sample_masktex(const Scene *scene, Brush *br,
y = flen * sinf(angle);
}
- if (fabsf(x) > br->stencil_dimension[0] || fabsf(y) > br->stencil_dimension[1]) {
+ if (fabsf(x) > br->mask_stencil_dimension[0] || fabsf(y) > br->mask_stencil_dimension[1]) {
zero_v4(rgba);
return 0.0f;
}
- x /= (br->stencil_dimension[0]);
- y /= (br->stencil_dimension[1]);
+ x /= (br->mask_stencil_dimension[0]);
+ y /= (br->mask_stencil_dimension[1]);
x *= mtex->size[0];
y *= mtex->size[1];
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index 806ca280789..466c0b6dcb2 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -9318,6 +9318,12 @@ static void do_versions(FileData *fd, Library *lib, Main *main)
brush->stencil_pos[0] = 256;
brush->stencil_pos[1] = 256;
}
+ if (brush->mask_stencil_dimension[0] == 0) {
+ brush->mask_stencil_dimension[0] = 256;
+ brush->mask_stencil_dimension[1] = 256;
+ brush->mask_stencil_pos[0] = 256;
+ brush->mask_stencil_pos[1] = 256;
+ }
}
/* TIP: to initialize new variables added, use the new function
diff --git a/source/blender/editors/sculpt_paint/paint_cursor.c b/source/blender/editors/sculpt_paint/paint_cursor.c
index 49863621b04..2f49433d5bb 100644
--- a/source/blender/editors/sculpt_paint/paint_cursor.c
+++ b/source/blender/editors/sculpt_paint/paint_cursor.c
@@ -585,14 +585,24 @@ static void paint_draw_tex_overlay(UnifiedPaintSettings *ups, Brush *brush,
}
/* Stencil code goes here */
else {
- quad.xmin = -brush->stencil_dimension[0];
- quad.ymin = -brush->stencil_dimension[1];
- quad.xmax = brush->stencil_dimension[0];
- quad.ymax = brush->stencil_dimension[1];
-
+ if (primary) {
+ quad.xmin = -brush->stencil_dimension[0];
+ quad.ymin = -brush->stencil_dimension[1];
+ quad.xmax = brush->stencil_dimension[0];
+ quad.ymax = brush->stencil_dimension[1];
+ }
+ else {
+ quad.xmin = -brush->mask_stencil_dimension[0];
+ quad.ymin = -brush->mask_stencil_dimension[1];
+ quad.xmax = brush->mask_stencil_dimension[0];
+ quad.ymax = brush->mask_stencil_dimension[1];
+ }
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
- glTranslatef(brush->stencil_pos[0], brush->stencil_pos[1], 0);
+ if (primary)
+ glTranslatef(brush->stencil_pos[0], brush->stencil_pos[1], 0);
+ else
+ glTranslatef(brush->mask_stencil_pos[0], brush->mask_stencil_pos[1], 0);
glRotatef(RAD2DEGF(mtex->rot), 0, 0, 1);
glMatrixMode(GL_TEXTURE);
}
diff --git a/source/blender/editors/sculpt_paint/paint_ops.c b/source/blender/editors/sculpt_paint/paint_ops.c
index ae49fbcbc95..f0265fd4e69 100644
--- a/source/blender/editors/sculpt_paint/paint_ops.c
+++ b/source/blender/editors/sculpt_paint/paint_ops.c
@@ -451,14 +451,20 @@ static void BRUSH_OT_uv_sculpt_tool_set(wmOperatorType *ot)
/***** Stencil Control *****/
typedef enum {
-STENCIL_TRANSLATE,
-STENCIL_SCALE,
-STENCIL_ROTATE
+ STENCIL_TRANSLATE,
+ STENCIL_SCALE,
+ STENCIL_ROTATE
} StencilControlMode;
typedef enum {
-STENCIL_CONSTRAINT_X = 1,
-STENCIL_CONSTRAINT_Y = 2
+ STENCIL_PRIMARY = 0,
+ STENCIL_SECONDARY = 1
+} StencilTextureMode;
+
+
+typedef enum {
+ STENCIL_CONSTRAINT_X = 1,
+ STENCIL_CONSTRAINT_Y = 2
} StencilConstraint;
typedef struct {
@@ -471,48 +477,92 @@ typedef struct {
float area_size[2];
StencilControlMode mode;
StencilConstraint constrain_mode;
+ int mask; /* we are twaking mask or colour stencil */
Brush *br;
+ float *dim_target;
+ float *rot_target;
+ float *pos_target;
short event_type;
} StencilControlData;
+static void stencil_set_target(StencilControlData *scd)
+{
+ Brush *br = scd->br;
+ float mdiff[2];
+ if (scd->mask) {
+ copy_v2_v2(scd->init_sdim, br->mask_stencil_dimension);
+ copy_v2_v2(scd->init_spos, br->mask_stencil_pos);
+ scd->init_rot = br->mask_mtex.rot;
+
+ scd->dim_target = br->mask_stencil_dimension;
+ scd->rot_target = &br->mask_mtex.rot;
+ scd->pos_target = br->mask_stencil_pos;
+ } else {
+ copy_v2_v2(scd->init_sdim, br->stencil_dimension);
+ copy_v2_v2(scd->init_spos, br->stencil_pos);
+ scd->init_rot = br->mtex.rot;
+
+ scd->dim_target = br->stencil_dimension;
+ scd->rot_target = &br->mtex.rot;
+ scd->pos_target = br->stencil_pos;
+ }
+
+ sub_v2_v2v2(mdiff, scd->init_mouse, br->stencil_pos);
+ scd->lenorig = len_v2(mdiff);
+
+ scd->init_angle = atan2(mdiff[1], mdiff[0]);
+}
+
static int stencil_control_invoke(bContext *C, wmOperator *op, const wmEvent *event)
{
Paint *paint = BKE_paint_get_active_from_context(C);
Brush *br = BKE_paint_brush(paint);
- float mdiff[2];
float mvalf[2] = {event->mval[0], event->mval[1]};
ARegion *ar = CTX_wm_region(C);
+ StencilControlData *scd;
+ int mask = RNA_enum_get(op->ptr, "texmode");
+
+ if (mask) {
+ if (br->mask_mtex.brush_map_mode != MTEX_MAP_MODE_STENCIL)
+ return OPERATOR_CANCELLED;
+ }
+ else {
+ if (br->mtex.brush_map_mode != MTEX_MAP_MODE_STENCIL)
+ return OPERATOR_CANCELLED;
+ }
- StencilControlData *scd = MEM_mallocN(sizeof(StencilControlData), "stencil_control");
+ scd = MEM_mallocN(sizeof(StencilControlData), "stencil_control");
+ scd->mask = mask;
+ scd->br = br;
copy_v2_v2(scd->init_mouse, mvalf);
- copy_v2_v2(scd->init_sdim, br->stencil_dimension);
- copy_v2_v2(scd->init_spos, br->stencil_pos);
- sub_v2_v2v2(mdiff, mvalf, br->stencil_pos);
- scd->lenorig = len_v2(mdiff);
- scd->br = br;
- scd->init_rot = br->mtex.rot;
- scd->init_angle = atan2(mdiff[1], mdiff[0]);
+
+ stencil_set_target(scd);
+
scd->mode = RNA_enum_get(op->ptr, "mode");
scd->event_type = event->type;
scd->area_size[0] = ar->winx;
scd->area_size[1] = ar->winy;
+
op->customdata = scd;
WM_event_add_modal_handler(C, op);
return OPERATOR_RUNNING_MODAL;
}
+static void stencil_restore(StencilControlData *scd)
+{
+ copy_v2_v2(scd->dim_target, scd->init_sdim);
+ copy_v2_v2(scd->pos_target, scd->init_spos);
+ *scd->rot_target = scd->init_rot;
+}
static int stencil_control_cancel(bContext *UNUSED(C), wmOperator *op)
{
StencilControlData *scd = op->customdata;
- Brush *br = scd->br;
- copy_v2_v2(br->stencil_dimension, scd->init_sdim);
- copy_v2_v2(br->stencil_pos, scd->init_spos);
- br->mtex.rot = scd->init_rot;
+ stencil_restore(scd);
MEM_freeN(op->customdata);
return OPERATOR_CANCELLED;
}
@@ -526,21 +576,21 @@ static void stencil_control_calculate(StencilControlData *scd, const int mval[2]
switch (scd->mode) {
case STENCIL_TRANSLATE:
sub_v2_v2v2(mdiff, mvalf, scd->init_mouse);
- add_v2_v2v2(scd->br->stencil_pos, scd->init_spos,
+ add_v2_v2v2(scd->pos_target, scd->init_spos,
mdiff);
- CLAMP(scd->br->stencil_pos[0],
- -scd->br->stencil_dimension[0] + PIXEL_MARGIN,
- scd->area_size[0] + scd->br->stencil_dimension[0] - PIXEL_MARGIN);
+ CLAMP(scd->pos_target[0],
+ -scd->dim_target[0] + PIXEL_MARGIN,
+ scd->area_size[0] + scd->dim_target[0] - PIXEL_MARGIN);
- CLAMP(scd->br->stencil_pos[1],
- -scd->br->stencil_dimension[1] + PIXEL_MARGIN,
- scd->area_size[1] + scd->br->stencil_dimension[1] - PIXEL_MARGIN);
+ CLAMP(scd->pos_target[1],
+ -scd->dim_target[1] + PIXEL_MARGIN,
+ scd->area_size[1] + scd->dim_target[1] - PIXEL_MARGIN);
break;
case STENCIL_SCALE:
{
float len, factor;
- sub_v2_v2v2(mdiff, mvalf, scd->br->stencil_pos);
+ sub_v2_v2v2(mdiff, mvalf, scd->pos_target);
len = len_v2(mdiff);
factor = len / scd->lenorig;
copy_v2_v2(mdiff, scd->init_sdim);
@@ -548,20 +598,22 @@ static void stencil_control_calculate(StencilControlData *scd, const int mval[2]
mdiff[0] = factor * scd->init_sdim[0];
if (scd->constrain_mode != STENCIL_CONSTRAINT_X)
mdiff[1] = factor * scd->init_sdim[1];
- copy_v2_v2(scd->br->stencil_dimension, mdiff);
+ CLAMP(mdiff[0], 5.0, 10000);
+ CLAMP(mdiff[1], 5.0, 10000);
+ copy_v2_v2(scd->dim_target, mdiff);
break;
}
case STENCIL_ROTATE:
{
float angle;
- sub_v2_v2v2(mdiff, mvalf, scd->br->stencil_pos);
+ sub_v2_v2v2(mdiff, mvalf, scd->pos_target);
angle = atan2(mdiff[1], mdiff[0]);
angle = scd->init_rot + angle - scd->init_angle;
if (angle < 0.0f)
angle += (float)(2 * M_PI);
if (angle > (float)(2 * M_PI))
angle -= (float)(2 * M_PI);
- scd->br->mtex.rot = angle;
+ *scd->rot_target = angle;
break;
}
}
@@ -623,7 +675,9 @@ static int stencil_control_poll(bContext *C)
Paint *paint = BKE_paint_get_active_from_context(C);
Brush *br = BKE_paint_brush(paint);
- return (br && br->mtex.brush_map_mode == MTEX_MAP_MODE_STENCIL);
+ return (br &&
+ (br->mtex.brush_map_mode == MTEX_MAP_MODE_STENCIL ||
+ br->mask_mtex.brush_map_mode == MTEX_MAP_MODE_STENCIL));
}
static void BRUSH_OT_stencil_control(wmOperatorType *ot)
@@ -634,6 +688,12 @@ static void BRUSH_OT_stencil_control(wmOperatorType *ot)
{STENCIL_ROTATE, "ROTATION", 0, "Rotation", ""},
{0, NULL, 0, NULL, NULL}
};
+
+ static EnumPropertyItem stencil_texture_items[] = {
+ {STENCIL_PRIMARY, "PRIMARY", 0, "Primary", ""},
+ {STENCIL_SECONDARY, "SECONDARY", 0, "Secondary", ""},
+ {0, NULL, 0, NULL, NULL}
+ };
/* identifiers */
ot->name = "Stencil Brush Control";
ot->description = "Control the stencil brush";
@@ -648,7 +708,8 @@ static void BRUSH_OT_stencil_control(wmOperatorType *ot)
/* flags */
ot->flag = 0;
- RNA_def_enum(ot->srna, "mode", stencil_control_items, 0, "Tool", "");
+ RNA_def_enum(ot->srna, "mode", stencil_control_items, STENCIL_TRANSLATE, "Tool", "");
+ RNA_def_enum(ot->srna, "texmode", stencil_texture_items, STENCIL_PRIMARY, "Tool", "");
}
@@ -721,6 +782,15 @@ static void ed_keymap_stencil(wmKeyMap *keymap)
kmi = WM_keymap_add_item(keymap, "BRUSH_OT_stencil_control", RIGHTMOUSE, KM_PRESS, KM_CTRL, 0);
RNA_enum_set(kmi->ptr, "mode", STENCIL_ROTATE);
+ kmi = WM_keymap_add_item(keymap, "BRUSH_OT_stencil_control", RIGHTMOUSE, KM_PRESS, KM_ALT, 0);
+ RNA_enum_set(kmi->ptr, "mode", STENCIL_TRANSLATE);
+ RNA_enum_set(kmi->ptr, "texmode", STENCIL_SECONDARY);
+ kmi = WM_keymap_add_item(keymap, "BRUSH_OT_stencil_control", RIGHTMOUSE, KM_PRESS, KM_SHIFT | KM_ALT, 0);
+ RNA_enum_set(kmi->ptr, "texmode", STENCIL_SECONDARY);
+ RNA_enum_set(kmi->ptr, "mode", STENCIL_SCALE);
+ kmi = WM_keymap_add_item(keymap, "BRUSH_OT_stencil_control", RIGHTMOUSE, KM_PRESS, KM_CTRL | KM_ALT, 0);
+ RNA_enum_set(kmi->ptr, "texmode", STENCIL_SECONDARY);
+ RNA_enum_set(kmi->ptr, "mode", STENCIL_ROTATE);
}
/**************************** registration **********************************/
diff --git a/source/blender/makesdna/DNA_brush_types.h b/source/blender/makesdna/DNA_brush_types.h
index 2ed6b29caec..c37758fb940 100644
--- a/source/blender/makesdna/DNA_brush_types.h
+++ b/source/blender/makesdna/DNA_brush_types.h
@@ -111,6 +111,9 @@ typedef struct Brush {
float stencil_pos[2];
float stencil_dimension[2];
+
+ float mask_stencil_pos[2];
+ float mask_stencil_dimension[2];
} Brush;
/* Brush.flag */
diff --git a/source/blender/makesrna/intern/rna_brush.c b/source/blender/makesrna/intern/rna_brush.c
index 8e6bb976283..66a5ed947d7 100644
--- a/source/blender/makesrna/intern/rna_brush.c
+++ b/source/blender/makesrna/intern/rna_brush.c
@@ -855,6 +855,18 @@ static void rna_def_brush(BlenderRNA *brna)
RNA_def_property_ui_text(prop, "Stencil Dimensions", "Dimensions of stencil in viewport");
RNA_def_property_update(prop, 0, "rna_Brush_update");
+ prop = RNA_def_property(srna, "mask_stencil_pos", PROP_FLOAT, PROP_XYZ);
+ RNA_def_property_float_sdna(prop, NULL, "mask_stencil_pos");
+ RNA_def_property_array(prop, 2);
+ RNA_def_property_ui_text(prop, "Mask Stencil Position", "Position of mask stencil in viewport");
+ RNA_def_property_update(prop, 0, "rna_Brush_update");
+
+ prop = RNA_def_property(srna, "mask_stencil_dimension", PROP_FLOAT, PROP_XYZ);
+ RNA_def_property_float_sdna(prop, NULL, "mask_stencil_dimension");
+ RNA_def_property_array(prop, 2);
+ RNA_def_property_ui_text(prop, "Mask Stencil Dimensions", "Dimensions of mask stencil in viewport");
+ RNA_def_property_update(prop, 0, "rna_Brush_update");
+
/* flag */
prop = RNA_def_property(srna, "use_airbrush", PROP_BOOLEAN, PROP_NONE);
RNA_def_property_boolean_sdna(prop, NULL, "flag", BRUSH_AIRBRUSH);