[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [20542] branches/soc-2009-yukishiro/source /blender: start adding some operators for light paint
Jingyuan Huang
jingyuan.huang at gmail.com
Mon Jun 1 06:02:44 CEST 2009
Revision: 20542
http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=20542
Author: yukishiro
Date: 2009-06-01 06:02:44 +0200 (Mon, 01 Jun 2009)
Log Message:
-----------
start adding some operators for light paint
Modified Paths:
--------------
branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_intern.h
branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_light.c
branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_ops.c
branches/soc-2009-yukishiro/source/blender/editors/space_view3d/drawobject.c
branches/soc-2009-yukishiro/source/blender/editors/space_view3d/space_view3d.c
branches/soc-2009-yukishiro/source/blender/editors/space_view3d/view3d_ops.c
branches/soc-2009-yukishiro/source/blender/makesdna/DNA_scene_types.h
branches/soc-2009-yukishiro/source/blender/makesdna/DNA_view3d_types.h
Modified: branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_intern.h
===================================================================
--- branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_intern.h 2009-05-31 21:14:25 UTC (rev 20541)
+++ branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_intern.h 2009-06-01 04:02:44 UTC (rev 20542)
@@ -56,6 +56,8 @@
/* paint_light.c */
void PAINT_OT_light_paint_toggle(struct wmOperatorType *ot);
+void PAINT_OT_light_paint(struct wmOperatorType *ot);
+void PAINT_OT_light_paint_radial_control(struct wmOperatorType *ot);
/* paint_utils.c */
int imapaint_pick_face(struct ViewContext *vc, struct Mesh *me, int *mval, unsigned int *index);
Modified: branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_light.c
===================================================================
--- branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_light.c 2009-05-31 21:14:25 UTC (rev 20541)
+++ branches/soc-2009-yukishiro/source/blender/editors/sculpt_paint/paint_light.c 2009-06-01 04:02:44 UTC (rev 20542)
@@ -76,6 +76,9 @@
#include "paint_intern.h"
+#define MAXINDEX 512000
+
+
typedef struct ShJob {
Scene *scene;
View3D *v3d;
@@ -83,6 +86,8 @@
short *do_update;
} ShJob;
+extern unsigned int rgba_to_mcol(float r, float g, float b, float a);
+
static void sh_freejob(void *sjv)
{
ShJob *sj= sjv;
@@ -100,59 +105,158 @@
SH_ComputeSceneCoefficients(sj->scene, sj->v3d);
}
-static void toggle_paint_cursor(bContext *C, int enable)
-{
- // TODO
- //ToolSettings *settings= CTX_data_scene(C)->toolsettings;
- //if(settings->imapaint.paintcursor && !enable) {
- // WM_paint_cursor_end(CTX_wm_manager(C), settings->imapaint.paintcursor);
- // settings->imapaint.paintcursor = NULL;
- //}
- //else if(enable)
- // settings->imapaint.paintcursor= WM_paint_cursor_activate(CTX_wm_manager(C), image_paint_poll, brush_drawcursor, NULL);
-}
-
-
// TODO: problem with using a job for the scene is that info header would display a render button....
-// TODO: somehow starting a job sometimes causes the application to hang. need investigation
+// TODO: view3d display should wait till this job finishes.
static void initial_computation(bContext *C)
{
Scene *scene= CTX_data_scene(C);
SH_ComputeSceneCoefficients(scene, CTX_wm_view3d(C));
- //wmJob *job;
- //ShJob *sj;
+// wmJob *job;
+// ShJob *sj;
+//
+// /* only one job at a time */
+// if(WM_jobs_test(CTX_wm_manager(C), scene)) return;
+//
+// /* handle UI stuff */
+// WM_cursor_wait(1);
+//
+// /* job custom data */
+// sj= MEM_callocN(sizeof(ShJob), "SH job");
+// sj->scene= scene;
+// sj->v3d= CTX_wm_view3d(C);
+//
+// /* setup job */
+// job= WM_jobs_get(CTX_wm_manager(C), CTX_wm_window(C), scene);
+// WM_jobs_customdata(job, sj, sh_freejob);
+// WM_jobs_timer(job, 0.2, NC_SCENE|ND_SH_RESULT, 0);
+// WM_jobs_callbacks(job, sh_startjob, NULL, NULL);
+//
+// /* start job */
+// WM_jobs_start(job);
+// WM_cursor_wait(0);
+}
- ///* only one job at a time */
- //if(WM_jobs_test(CTX_wm_manager(C), scene)) return;
+static int *get_indexarray(void)
+{
+ return MEM_mallocN(sizeof(int)*MAXINDEX + 2, "lightpaint");
+}
- ///* handle UI stuff */
- //WM_cursor_wait(1);
+static unsigned int lpaint_get_current_col(VPaint *lp)
+{
+ return rgba_to_mcol(lp->brush->rgb[0], lp->brush->rgb[1], lp->brush->rgb[2], 1.0f);
+}
- ///* job custom data */
- //sj= MEM_callocN(sizeof(ShJob), "SH job");
- //sj->scene= scene;
- //sj->v3d= CTX_wm_view3d(C);
+/************************ light paint poll ************************/
- ///* setup job */
- //job= WM_jobs_get(CTX_wm_manager(C), CTX_wm_window(C), scene);
- //WM_jobs_customdata(job, sj, sh_freejob);
- //WM_jobs_timer(job, 0.2, NC_SCENE|ND_SH_RESULT, 0);
- //WM_jobs_callbacks(job, sh_startjob, NULL, NULL);
+static int light_paint_poll(bContext *C)
+{
+ if(CTX_wm_region_view3d(C)) return 1;
- ///* start job */
- //WM_jobs_start(job);
- //WM_cursor_wait(0);
+ return 0;
}
+static int lp_poll(bContext *C)
+{
+ if(G.f & G_LIGHTPAINT) {
+ ScrArea *sa= CTX_wm_area(C);
+ if(sa->spacetype==SPACE_VIEW3D) {
+ ARegion *ar= CTX_wm_region(C);
+ if(ar->regiontype==RGN_TYPE_WINDOW)
+ return 1;
+ }
+ }
+ return 0;
+}
+/* Cursor */
+static void lp_drawcursor(bContext *C, int x, int y, void *customdata)
+{
+ ToolSettings *ts= CTX_data_tool_settings(C);
+
+ glTranslatef((float)x, (float)y, 0.0f);
+
+ glColor4ub(255, 255, 255, 128);
+ glEnable( GL_LINE_SMOOTH );
+ glEnable(GL_BLEND);
+ glutil_draw_lined_arc(0.0, M_PI*2.0, ts->lpaint->brush->size, 40);
+ glDisable(GL_BLEND);
+ glDisable( GL_LINE_SMOOTH );
+
+ glTranslatef((float)-x, (float)-y, 0.0f);
+}
+
+static void toggle_paint_cursor(bContext *C)
+{
+ ToolSettings *ts = CTX_data_scene(C)->toolsettings;
+ VPaint *lp = ts->lpaint;
+
+ if(lp->paintcursor) {
+ WM_paint_cursor_end(CTX_wm_manager(C), lp->paintcursor);
+ lp->paintcursor = NULL;
+ }
+ else {
+ lp->paintcursor= WM_paint_cursor_activate(CTX_wm_manager(C), lp_poll, lp_drawcursor, NULL);
+ }
+}
+
+static VPaint *new_lpaint()
+{
+ VPaint *vp= MEM_callocN(sizeof(VPaint), "VPaint");
+
+ vp->gamma= vp->mul= 1.0f;
+ vp->flag= VP_AREA+VP_SOFT+VP_SPRAY; //TODO: not sure how to use flag for light brush
+ return vp;
+}
+
static int light_paint_toggle_exec(bContext *C, wmOperator *op)
{
Scene *scene= CTX_data_scene(C);
+ View3D *v3d= CTX_wm_view3d(C);
+ VPaint *lp= scene->toolsettings->lpaint;
+ Base *base= NULL;
+ Object *ob;
+ Mesh *me;
+ DerivedMesh *dm;
+ int totface= 0;
+ for (base = scene->basact; base; base = base->next) {
+ ob = base->object;
+ me = get_mesh(ob);
+ if (me == NULL) continue;
+
+ dm = mesh_get_derived_final(scene, ob, v3d->customdata_mask);
+ totface += dm->getNumFaces(dm);
+ }
+
+ if (totface == 0) {
+ G.f &= ~G_LIGHTPAINT;
+ return OPERATOR_FINISHED;
+ }
+
+ // TODO: need to signal/flag if the paint is for the entire scene or just the active object
+ if(totface >= MAXINDEX) {
+ ob= CTX_data_active_object(C);
+ me= get_mesh(ob);
+
+ if(me==NULL || object_data_is_libdata(ob)) {
+ G.f &= ~G_VERTEXPAINT;
+ return OPERATOR_FINISHED;
+ }
+ if(me && me->totface>=MAXINDEX) {
+ // TODO: output error message or pop out error message
+ printf("Maximum number of faces: %d", MAXINDEX-1);
+ G.f &= ~G_VERTEXPAINT;
+ return OPERATOR_FINISHED;
+ }
+ }
+
if(G.f & G_LIGHTPAINT) {
G.f &= ~G_LIGHTPAINT;
- toggle_paint_cursor(C, 0);
+ if(lp) {
+ toggle_paint_cursor(C);
+ lp->paintcursor= NULL;
+ }
}
else {
G.f |= G_LIGHTPAINT;
@@ -161,22 +265,96 @@
initial_computation(C);
scene->flag |= SCE_SH_COMPUTED;
}
- toggle_paint_cursor(C, 1);
+ if(lp==NULL)
+ lp= scene->toolsettings->lpaint= new_lpaint();
+
+ toggle_paint_cursor(C);
+ brush_check_exists(&scene->toolsettings->lpaint->brush);
}
+ // TODO: add to depsgraph?
+
+ ED_area_tag_redraw(CTX_wm_area(C));
WM_event_add_notifier(C, NC_SCENE|ND_RENDER_RESULT, scene);
- ED_area_tag_redraw(CTX_wm_area(C));
return OPERATOR_FINISHED;
}
-static int light_paint_toggle_poll(bContext *C)
+/************************ light paint operator ************************/
+typedef struct PaintOperation {
+ ViewContext vc;
+ unsigned int paintcol;
+ int *indexar;
+ //float *vertexcosnos;
+} PaintOperation;
+
+static void lpaint_exit(bContext *C, wmOperator *op)
{
- if(CTX_wm_region_view3d(C)) return 1;
+ PaintOperation *pop= op->customdata;
+
+ MEM_freeN(pop->indexar);
+ MEM_freeN(pop);
+ op->customdata= NULL;
+}
- return 0;
+static int light_paint_modal(bContext *C, wmOperator *op, wmEvent *event)
+{
+ switch(event->type) {
+ case LEFTMOUSE:
+ if(event->val==0) { /* release */
+ lpaint_exit(C, op);
+ return OPERATOR_FINISHED;
+ }
+ /* pass on, first press gets painted too */
+
+ case MOUSEMOVE:
+ break;
+ }
+
+ return OPERATOR_RUNNING_MODAL;
}
+static int light_paint_invoke(bContext *C, wmOperator *op, wmEvent *event)
+{
+ PaintOperation *pop;
+ ToolSettings *ts= CTX_data_tool_settings(C);
+ VPaint *lp= ts->lpaint;
+ printf("invoked\n");
+ op->customdata= pop = MEM_callocN(sizeof(struct PaintOperation), "LightPOP");
+ view3d_set_viewcontext(C, &pop->vc);
+
+ pop->indexar= get_indexarray();
+ pop->paintcol= lpaint_get_current_col(lp);
+
+ light_paint_modal(C, op, event);
+
+ WM_event_add_modal_handler(C, &CTX_wm_window(C)->handlers, op);
+
+ return OPERATOR_RUNNING_MODAL;
+}
+
+/************************ light paint radial operator ************************/
+static int lpaint_radial_control_invoke(bContext *C, wmOperator *op, wmEvent *event)
+{
+ toggle_paint_cursor(C);
+ brush_radial_control_invoke(op, CTX_data_scene(C)->toolsettings->lpaint->brush, 1);
+ return WM_radial_control_invoke(C, op, event);
+}
+
+static int lpaint_radial_control_modal(bContext *C, wmOperator *op, wmEvent *event)
+{
+ int ret = WM_radial_control_modal(C, op, event);
+ if(ret != OPERATOR_RUNNING_MODAL)
+ toggle_paint_cursor(C);
+ return ret;
+}
+
+static int lpaint_radial_control_exec(bContext *C, wmOperator *op)
+{
+ return brush_radial_control_exec(op, CTX_data_scene(C)->toolsettings->lpaint->brush, 1);
+}
+
+
void PAINT_OT_light_paint_toggle(wmOperatorType *ot)
{
/* identifiers */
@@ -185,8 +363,44 @@
/* api callbacks */
ot->exec= light_paint_toggle_exec;
- ot->poll= light_paint_toggle_poll;
+ ot->poll= light_paint_poll;
/* flags */
ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO;
}
+
+void PAINT_OT_light_paint(wmOperatorType *ot)
+{
+ /* identifiers */
+ ot->name= "Light Paint";
+ ot->idname= "PAINT_OT_light_paint";
+
+ /* api callbacks */
+ //ot->exec= light_paint_exec;
+ ot->invoke= light_paint_invoke;
+ ot->modal= light_paint_modal;
+ //ot->cancel= light_paint_cancel;
+ ot->poll= light_paint_poll;
+
+ /* flags */
+ ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO;
+
+ /* properties */
+ //RNA_def_collection_runtime(ot->srna, "stroke", &RNA_OperatorStrokeElement, "Stroke", "");
+}
+
+void PAINT_OT_light_paint_radial_control(wmOperatorType *ot)
+{
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list