| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | /*
 | 
					
						
							|  |  |  |  * This program is free software; you can redistribute it and/or | 
					
						
							|  |  |  |  * modify it under the terms of the GNU General Public License | 
					
						
							|  |  |  |  * as published by the Free Software Foundation; either version 2 | 
					
						
							|  |  |  |  * of the License, or (at your option) any later version. | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * This program is distributed in the hope that it will be useful, | 
					
						
							|  |  |  |  * but WITHOUT ANY WARRANTY; without even the implied warranty of | 
					
						
							|  |  |  |  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the | 
					
						
							|  |  |  |  * GNU General Public License for more details. | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * You should have received a copy of the GNU General Public License | 
					
						
							|  |  |  |  * along with this program; if not, write to the Free Software Foundation, | 
					
						
							|  |  |  |  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. | 
					
						
							|  |  |  |  * | 
					
						
							| 
									
										
										
										
											2019-01-23 11:29:18 +11:00
										 |  |  |  * Copyright 2016, Blender Foundation. | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-02-18 08:08:12 +11:00
										 |  |  | /** \file
 | 
					
						
							|  |  |  |  * \ingroup draw | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  |  * | 
					
						
							|  |  |  |  * Contains dynamic drawing using immediate mode | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #include "DNA_brush_types.h"
 | 
					
						
							|  |  |  | #include "DNA_screen_types.h"
 | 
					
						
							|  |  |  | #include "DNA_userdef_types.h"
 | 
					
						
							|  |  |  | #include "DNA_view3d_types.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #include "ED_screen.h"
 | 
					
						
							|  |  |  | #include "ED_view3d.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #include "GPU_immediate.h"
 | 
					
						
							|  |  |  | #include "GPU_matrix.h"
 | 
					
						
							| 
									
										
										
										
											2020-03-19 09:33:03 +01:00
										 |  |  | #include "GPU_shader.h"
 | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | #include "UI_resources.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-04-07 00:35:57 +10:00
										 |  |  | #include "WM_types.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | #include "BKE_object.h"
 | 
					
						
							|  |  |  | #include "BKE_paint.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #include "view3d_intern.h"
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-10-05 17:18:41 +02:00
										 |  |  | #include "draw_manager.h"
 | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | /* ******************** region info ***************** */ | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | void DRW_draw_region_info(void) | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   const DRWContextState *draw_ctx = DRW_context_state_get(); | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   ARegion *region = draw_ctx->region; | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   DRW_draw_cursor(); | 
					
						
							| 
									
										
										
										
											2017-05-04 15:46:09 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   view3d_draw_region_info(draw_ctx->evil_C, region); | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | /* **************************** 3D Cursor ******************************** */ | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-02-06 16:10:03 +11:00
										 |  |  | static bool is_cursor_visible(const DRWContextState *draw_ctx, Scene *scene, ViewLayer *view_layer) | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | { | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   View3D *v3d = draw_ctx->v3d; | 
					
						
							|  |  |  |   if ((v3d->flag2 & V3D_HIDE_OVERLAYS) || (v3d->overlay.flag & V3D_OVERLAY_HIDE_CURSOR)) { | 
					
						
							|  |  |  |     return false; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   /* don't draw cursor in paint modes, but with a few exceptions */ | 
					
						
							|  |  |  |   if (draw_ctx->object_mode & OB_MODE_ALL_PAINT) { | 
					
						
							|  |  |  |     /* exception: object is in weight paint and has deforming armature in pose mode */ | 
					
						
							|  |  |  |     if (draw_ctx->object_mode & OB_MODE_WEIGHT_PAINT) { | 
					
						
							|  |  |  |       if (BKE_object_pose_armature_get(draw_ctx->obact) != NULL) { | 
					
						
							|  |  |  |         return true; | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     /* exception: object in texture paint mode, clone brush, use_clone_layer disabled */ | 
					
						
							|  |  |  |     else if (draw_ctx->object_mode & OB_MODE_TEXTURE_PAINT) { | 
					
						
							|  |  |  |       const Paint *p = BKE_paint_get_active(scene, view_layer); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       if (p && p->brush && p->brush->imagepaint_tool == PAINT_TOOL_CLONE) { | 
					
						
							|  |  |  |         if ((scene->toolsettings->imapaint.flag & IMAGEPAINT_PROJECT_LAYER_CLONE) == 0) { | 
					
						
							|  |  |  |           return true; | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     /* no exception met? then don't draw cursor! */ | 
					
						
							|  |  |  |     return false; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  |   else if (draw_ctx->object_mode & OB_MODE_WEIGHT_GPENCIL) { | 
					
						
							|  |  |  |     /* grease pencil hide always in some modes */ | 
					
						
							|  |  |  |     return false; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   return true; | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | void DRW_draw_cursor(void) | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   const DRWContextState *draw_ctx = DRW_context_state_get(); | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   ARegion *region = draw_ctx->region; | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   Scene *scene = draw_ctx->scene; | 
					
						
							|  |  |  |   ViewLayer *view_layer = draw_ctx->view_layer; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-07-16 04:16:10 +02:00
										 |  |  |   GPU_color_mask(true, true, true, true); | 
					
						
							|  |  |  |   GPU_depth_mask(false); | 
					
						
							|  |  |  |   GPU_depth_test(false); | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |   if (is_cursor_visible(draw_ctx, scene, view_layer)) { | 
					
						
							|  |  |  |     int co[2]; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     /* Get cursor data into quaternion form */ | 
					
						
							|  |  |  |     const View3DCursor *cursor = &scene->cursor; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     if (ED_view3d_project_int_global( | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |             region, cursor->location, co, V3D_PROJ_TEST_NOP | V3D_PROJ_TEST_CLIP_NEAR) == | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |         V3D_PROJ_RET_OK) { | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |       RegionView3D *rv3d = region->regiondata; | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |       float cursor_quat[4]; | 
					
						
							|  |  |  |       BKE_scene_cursor_rot_to_quat(cursor, cursor_quat); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       /* Draw nice Anti Aliased cursor. */ | 
					
						
							|  |  |  |       GPU_line_width(1.0f); | 
					
						
							|  |  |  |       GPU_blend(true); | 
					
						
							|  |  |  |       GPU_line_smooth(true); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       float eps = 1e-5f; | 
					
						
							|  |  |  |       rv3d->viewquat[0] = -rv3d->viewquat[0]; | 
					
						
							|  |  |  |       bool is_aligned = compare_v4v4(cursor_quat, rv3d->viewquat, eps); | 
					
						
							|  |  |  |       if (is_aligned == false) { | 
					
						
							|  |  |  |         float tquat[4]; | 
					
						
							|  |  |  |         rotation_between_quats_to_quat(tquat, rv3d->viewquat, cursor_quat); | 
					
						
							|  |  |  |         is_aligned = tquat[0] - eps < -1.0f; | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |       rv3d->viewquat[0] = -rv3d->viewquat[0]; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       /* Draw lines */ | 
					
						
							|  |  |  |       if (is_aligned == false) { | 
					
						
							|  |  |  |         uint pos = GPU_vertformat_attr_add( | 
					
						
							|  |  |  |             immVertexFormat(), "pos", GPU_COMP_F32, 3, GPU_FETCH_FLOAT); | 
					
						
							|  |  |  |         immBindBuiltinProgram(GPU_SHADER_3D_UNIFORM_COLOR); | 
					
						
							|  |  |  |         immUniformThemeColor3(TH_VIEW_OVERLAY); | 
					
						
							|  |  |  |         immBegin(GPU_PRIM_LINES, 12); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         const float scale = ED_view3d_pixel_size_no_ui_scale(rv3d, cursor->location) * | 
					
						
							|  |  |  |                             U.widget_unit; | 
					
						
							| 
									
										
										
										
											2018-05-08 14:18:09 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | #define CURSOR_VERT(axis_vec, axis, fac) \
 | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   immVertex3f(pos, \ | 
					
						
							|  |  |  |               cursor->location[0] + axis_vec[0] * (fac), \ | 
					
						
							|  |  |  |               cursor->location[1] + axis_vec[1] * (fac), \ | 
					
						
							|  |  |  |               cursor->location[2] + axis_vec[2] * (fac)) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #define CURSOR_EDGE(axis_vec, axis, sign) \
 | 
					
						
							|  |  |  |   { \ | 
					
						
							|  |  |  |     CURSOR_VERT(axis_vec, axis, sign 1.0f); \ | 
					
						
							|  |  |  |     CURSOR_VERT(axis_vec, axis, sign 0.25f); \ | 
					
						
							|  |  |  |   } \ | 
					
						
							|  |  |  |   ((void)0) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         for (int axis = 0; axis < 3; axis++) { | 
					
						
							|  |  |  |           float axis_vec[3] = {0}; | 
					
						
							|  |  |  |           axis_vec[axis] = scale; | 
					
						
							|  |  |  |           mul_qt_v3(cursor_quat, axis_vec); | 
					
						
							|  |  |  |           CURSOR_EDGE(axis_vec, axis, +); | 
					
						
							|  |  |  |           CURSOR_EDGE(axis_vec, axis, -); | 
					
						
							|  |  |  |         } | 
					
						
							| 
									
										
										
										
											2018-05-08 14:18:09 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  | #undef CURSOR_VERT
 | 
					
						
							|  |  |  | #undef CURSOR_EDGE
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |         immEnd(); | 
					
						
							|  |  |  |         immUnbindProgram(); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       float original_proj[4][4]; | 
					
						
							|  |  |  |       GPU_matrix_projection_get(original_proj); | 
					
						
							|  |  |  |       GPU_matrix_push(); | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |       ED_region_pixelspace(region); | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |       GPU_matrix_translate_2f(co[0] + 0.5f, co[1] + 0.5f); | 
					
						
							|  |  |  |       GPU_matrix_scale_2f(U.widget_unit, U.widget_unit); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       GPUBatch *cursor_batch = DRW_cache_cursor_get(is_aligned); | 
					
						
							|  |  |  |       GPUShader *shader = GPU_shader_get_builtin_shader(GPU_SHADER_2D_FLAT_COLOR); | 
					
						
							| 
									
										
										
										
											2020-07-30 01:07:29 +02:00
										 |  |  |       GPU_batch_set_shader(cursor_batch, shader); | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |       GPU_batch_draw(cursor_batch); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |       GPU_blend(false); | 
					
						
							|  |  |  |       GPU_line_smooth(false); | 
					
						
							|  |  |  |       GPU_matrix_pop(); | 
					
						
							|  |  |  |       GPU_matrix_projection_set(original_proj); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-07-14 23:49:00 +02:00
										 |  |  | /* **************************** 3D Gizmo ******************************** */ | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-07-14 23:49:00 +02:00
										 |  |  | void DRW_draw_gizmo_3d(void) | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | { | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   const DRWContextState *draw_ctx = DRW_context_state_get(); | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   ARegion *region = draw_ctx->region; | 
					
						
							| 
									
										
										
										
											2017-08-03 15:12:47 +10:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   /* draw depth culled gizmos - gizmos need to be updated *after* view matrix was set up */ | 
					
						
							|  |  |  |   /* TODO depth culling gizmos is not yet supported, just drawing _3D here, should
 | 
					
						
							|  |  |  |    * later become _IN_SCENE (and draw _3D separate) */ | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   WM_gizmomap_draw(region->gizmo_map, draw_ctx->evil_C, WM_GIZMOMAP_DRAWSTEP_3D); | 
					
						
							| 
									
										
										
										
											2017-12-16 18:55:42 +11:00
										 |  |  | } | 
					
						
							| 
									
										
										
										
											2017-08-03 15:12:47 +10:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2018-07-14 23:49:00 +02:00
										 |  |  | void DRW_draw_gizmo_2d(void) | 
					
						
							| 
									
										
										
										
											2017-12-16 18:55:42 +11:00
										 |  |  | { | 
					
						
							| 
									
										
										
										
											2019-04-17 06:17:24 +02:00
										 |  |  |   const DRWContextState *draw_ctx = DRW_context_state_get(); | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   ARegion *region = draw_ctx->region; | 
					
						
							| 
									
										
										
										
											2017-08-03 15:12:47 +10:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-03-06 16:56:42 +01:00
										 |  |  |   WM_gizmomap_draw(region->gizmo_map, draw_ctx->evil_C, WM_GIZMOMAP_DRAWSTEP_2D); | 
					
						
							| 
									
										
										
										
											2017-08-03 15:12:47 +10:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-07-16 04:16:10 +02:00
										 |  |  |   GPU_depth_mask(true); | 
					
						
							| 
									
										
										
										
											2017-02-14 17:48:16 +01:00
										 |  |  | } |