Cleanup: move keymap helpers into own file
[blender.git] / source / blender / windowmanager / intern / wm_keymap_utils.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * ***** END GPL LICENSE BLOCK *****
19  */
20
21 /** \file blender/windowmanager/intern/wm_keymap_utils.c
22  *  \ingroup wm
23  *
24  * Utilities to help define keymaps.
25  */
26
27 #include <string.h>
28
29 #include "DNA_object_types.h"
30 #include "DNA_space_types.h"
31 #include "DNA_userdef_types.h"
32 #include "DNA_windowmanager_types.h"
33
34 #include "BLI_utildefines.h"
35
36 #include "BKE_context.h"
37
38 #include "RNA_access.h"
39
40 #include "WM_api.h"
41 #include "WM_types.h"
42
43 /* menu wrapper for WM_keymap_add_item */
44
45 /* -------------------------------------------------------------------- */
46 /** \name Wrappers for #WM_keymap_add_item
47  * \{ */
48
49 wmKeyMapItem *WM_keymap_add_menu(wmKeyMap *keymap, const char *idname, int type, int val, int modifier, int keymodifier)
50 {
51         wmKeyMapItem *kmi = WM_keymap_add_item(keymap, "WM_OT_call_menu", type, val, modifier, keymodifier);
52         RNA_string_set(kmi->ptr, "name", idname);
53         return kmi;
54 }
55
56 wmKeyMapItem *WM_keymap_add_menu_pie(wmKeyMap *keymap, const char *idname, int type, int val, int modifier, int keymodifier)
57 {
58         wmKeyMapItem *kmi = WM_keymap_add_item(keymap, "WM_OT_call_menu_pie", type, val, modifier, keymodifier);
59         RNA_string_set(kmi->ptr, "name", idname);
60         return kmi;
61 }
62
63 /** \} */
64
65 /* -------------------------------------------------------------------- */
66 /** \name Introspection
67  * \{ */
68
69 /* Guess an appropriate keymap from the operator name */
70 /* Needs to be kept up to date with Keymap and Operator naming */
71 wmKeyMap *WM_keymap_guess_opname(const bContext *C, const char *opname)
72 {
73         /* Op types purposely skipped  for now:
74          *     BRUSH_OT
75          *     BOID_OT
76          *     BUTTONS_OT
77          *     CONSTRAINT_OT
78          *     PAINT_OT
79          *     ED_OT
80          *     FLUID_OT
81          *     TEXTURE_OT
82          *     UI_OT
83          *     VIEW2D_OT
84          *     WORLD_OT
85          */
86
87         wmKeyMap *km = NULL;
88         SpaceLink *sl = CTX_wm_space_data(C);
89
90         /* Window */
91         if (STRPREFIX(opname, "WM_OT")) {
92                 km = WM_keymap_find_all(C, "Window", 0, 0);
93         }
94         /* Screen & Render */
95         else if (STRPREFIX(opname, "SCREEN_OT") ||
96                  STRPREFIX(opname, "RENDER_OT") ||
97                  STRPREFIX(opname, "SOUND_OT") ||
98                  STRPREFIX(opname, "SCENE_OT"))
99         {
100                 km = WM_keymap_find_all(C, "Screen", 0, 0);
101         }
102         /* Grease Pencil */
103         else if (STRPREFIX(opname, "GPENCIL_OT")) {
104                 km = WM_keymap_find_all(C, "Grease Pencil", 0, 0);
105         }
106         /* Markers */
107         else if (STRPREFIX(opname, "MARKER_OT")) {
108                 km = WM_keymap_find_all(C, "Markers", 0, 0);
109         }
110         /* Import/Export*/
111         else if (STRPREFIX(opname, "IMPORT_") ||
112                  STRPREFIX(opname, "EXPORT_"))
113         {
114                 km = WM_keymap_find_all(C, "Window", 0, 0);
115         }
116
117
118         /* 3D View */
119         else if (STRPREFIX(opname, "VIEW3D_OT")) {
120                 km = WM_keymap_find_all(C, "3D View", sl->spacetype, 0);
121         }
122         else if (STRPREFIX(opname, "OBJECT_OT")) {
123                 /* exception, this needs to work outside object mode too */
124                 if (STRPREFIX(opname, "OBJECT_OT_mode_set"))
125                         km = WM_keymap_find_all(C, "Object Non-modal", 0, 0);
126                 else
127                         km = WM_keymap_find_all(C, "Object Mode", 0, 0);
128         }
129         /* Object mode related */
130         else if (STRPREFIX(opname, "GROUP_OT") ||
131                  STRPREFIX(opname, "MATERIAL_OT") ||
132                  STRPREFIX(opname, "PTCACHE_OT") ||
133                  STRPREFIX(opname, "RIGIDBODY_OT"))
134         {
135                 km = WM_keymap_find_all(C, "Object Mode", 0, 0);
136         }
137
138         /* Editing Modes */
139         else if (STRPREFIX(opname, "MESH_OT")) {
140                 km = WM_keymap_find_all(C, "Mesh", 0, 0);
141
142                 /* some mesh operators are active in object mode too, like add-prim */
143                 if (km && !WM_keymap_poll((bContext *)C, km)) {
144                         km = WM_keymap_find_all(C, "Object Mode", 0, 0);
145                 }
146         }
147         else if (STRPREFIX(opname, "CURVE_OT") ||
148                  STRPREFIX(opname, "SURFACE_OT"))
149         {
150                 km = WM_keymap_find_all(C, "Curve", 0, 0);
151
152                 /* some curve operators are active in object mode too, like add-prim */
153                 if (km && !WM_keymap_poll((bContext *)C, km)) {
154                         km = WM_keymap_find_all(C, "Object Mode", 0, 0);
155                 }
156         }
157         else if (STRPREFIX(opname, "ARMATURE_OT") ||
158                  STRPREFIX(opname, "SKETCH_OT"))
159         {
160                 km = WM_keymap_find_all(C, "Armature", 0, 0);
161         }
162         else if (STRPREFIX(opname, "POSE_OT") ||
163                  STRPREFIX(opname, "POSELIB_OT"))
164         {
165                 km = WM_keymap_find_all(C, "Pose", 0, 0);
166         }
167         else if (STRPREFIX(opname, "SCULPT_OT")) {
168                 switch (CTX_data_mode_enum(C)) {
169                         case OB_MODE_SCULPT:
170                                 km = WM_keymap_find_all(C, "Sculpt", 0, 0);
171                                 break;
172                         case OB_MODE_EDIT:
173                                 km = WM_keymap_find_all(C, "UV Sculpt", 0, 0);
174                                 break;
175                 }
176         }
177         else if (STRPREFIX(opname, "MBALL_OT")) {
178                 km = WM_keymap_find_all(C, "Metaball", 0, 0);
179
180                 /* some mball operators are active in object mode too, like add-prim */
181                 if (km && !WM_keymap_poll((bContext *)C, km)) {
182                         km = WM_keymap_find_all(C, "Object Mode", 0, 0);
183                 }
184         }
185         else if (STRPREFIX(opname, "LATTICE_OT")) {
186                 km = WM_keymap_find_all(C, "Lattice", 0, 0);
187         }
188         else if (STRPREFIX(opname, "PARTICLE_OT")) {
189                 km = WM_keymap_find_all(C, "Particle", 0, 0);
190         }
191         else if (STRPREFIX(opname, "FONT_OT")) {
192                 km = WM_keymap_find_all(C, "Font", 0, 0);
193         }
194         /* Paint Face Mask */
195         else if (STRPREFIX(opname, "PAINT_OT_face_select")) {
196                 km = WM_keymap_find_all(C, "Face Mask", 0, 0);
197         }
198         else if (STRPREFIX(opname, "PAINT_OT")) {
199                 /* check for relevant mode */
200                 switch (CTX_data_mode_enum(C)) {
201                         case OB_MODE_WEIGHT_PAINT:
202                                 km = WM_keymap_find_all(C, "Weight Paint", 0, 0);
203                                 break;
204                         case OB_MODE_VERTEX_PAINT:
205                                 km = WM_keymap_find_all(C, "Vertex Paint", 0, 0);
206                                 break;
207                         case OB_MODE_TEXTURE_PAINT:
208                                 km = WM_keymap_find_all(C, "Image Paint", 0, 0);
209                                 break;
210                 }
211         }
212         /* Timeline */
213         else if (STRPREFIX(opname, "TIME_OT")) {
214                 km = WM_keymap_find_all(C, "Timeline", sl->spacetype, 0);
215         }
216         /* Image Editor */
217         else if (STRPREFIX(opname, "IMAGE_OT")) {
218                 km = WM_keymap_find_all(C, "Image", sl->spacetype, 0);
219         }
220         /* Clip Editor */
221         else if (STRPREFIX(opname, "CLIP_OT")) {
222                 km = WM_keymap_find_all(C, "Clip", sl->spacetype, 0);
223         }
224         else if (STRPREFIX(opname, "MASK_OT")) {
225                 km = WM_keymap_find_all(C, "Mask Editing", 0, 0);
226         }
227         /* UV Editor */
228         else if (STRPREFIX(opname, "UV_OT")) {
229                 /* Hack to allow using UV unwrapping ops from 3DView/editmode.
230                  * Mesh keymap is probably not ideal, but best place I could find to put those. */
231                 if (sl->spacetype == SPACE_VIEW3D) {
232                         km = WM_keymap_find_all(C, "Mesh", 0, 0);
233                         if (km && !WM_keymap_poll((bContext *)C, km)) {
234                                 km = NULL;
235                         }
236                 }
237                 if (!km) {
238                         km = WM_keymap_find_all(C, "UV Editor", 0, 0);
239                 }
240         }
241         /* Node Editor */
242         else if (STRPREFIX(opname, "NODE_OT")) {
243                 km = WM_keymap_find_all(C, "Node Editor", sl->spacetype, 0);
244         }
245         /* Animation Editor Channels */
246         else if (STRPREFIX(opname, "ANIM_OT_channels")) {
247                 km = WM_keymap_find_all(C, "Animation Channels", 0, 0);
248         }
249         /* Animation Generic - after channels */
250         else if (STRPREFIX(opname, "ANIM_OT")) {
251                 km = WM_keymap_find_all(C, "Animation", 0, 0);
252         }
253         /* Graph Editor */
254         else if (STRPREFIX(opname, "GRAPH_OT")) {
255                 km = WM_keymap_find_all(C, "Graph Editor", sl->spacetype, 0);
256         }
257         /* Dopesheet Editor */
258         else if (STRPREFIX(opname, "ACTION_OT")) {
259                 km = WM_keymap_find_all(C, "Dopesheet", sl->spacetype, 0);
260         }
261         /* NLA Editor */
262         else if (STRPREFIX(opname, "NLA_OT")) {
263                 km = WM_keymap_find_all(C, "NLA Editor", sl->spacetype, 0);
264         }
265         /* Script */
266         else if (STRPREFIX(opname, "SCRIPT_OT")) {
267                 km = WM_keymap_find_all(C, "Script", sl->spacetype, 0);
268         }
269         /* Text */
270         else if (STRPREFIX(opname, "TEXT_OT")) {
271                 km = WM_keymap_find_all(C, "Text", sl->spacetype, 0);
272         }
273         /* Sequencer */
274         else if (STRPREFIX(opname, "SEQUENCER_OT")) {
275                 km = WM_keymap_find_all(C, "Sequencer", sl->spacetype, 0);
276         }
277         /* Console */
278         else if (STRPREFIX(opname, "CONSOLE_OT")) {
279                 km = WM_keymap_find_all(C, "Console", sl->spacetype, 0);
280         }
281         /* Console */
282         else if (STRPREFIX(opname, "INFO_OT")) {
283                 km = WM_keymap_find_all(C, "Info", sl->spacetype, 0);
284         }
285         /* File browser */
286         else if (STRPREFIX(opname, "FILE_OT")) {
287                 km = WM_keymap_find_all(C, "File Browser", sl->spacetype, 0);
288         }
289         /* Logic Editor */
290         else if (STRPREFIX(opname, "LOGIC_OT")) {
291                 km = WM_keymap_find_all(C, "Logic Editor", sl->spacetype, 0);
292         }
293         /* Outliner */
294         else if (STRPREFIX(opname, "OUTLINER_OT")) {
295                 km = WM_keymap_find_all(C, "Outliner", sl->spacetype, 0);
296         }
297         /* Transform */
298         else if (STRPREFIX(opname, "TRANSFORM_OT")) {
299                 /* check for relevant editor */
300                 switch (sl->spacetype) {
301                         case SPACE_VIEW3D:
302                                 km = WM_keymap_find_all(C, "3D View", sl->spacetype, 0);
303                                 break;
304                         case SPACE_IPO:
305                                 km = WM_keymap_find_all(C, "Graph Editor", sl->spacetype, 0);
306                                 break;
307                         case SPACE_ACTION:
308                                 km = WM_keymap_find_all(C, "Dopesheet", sl->spacetype, 0);
309                                 break;
310                         case SPACE_NLA:
311                                 km = WM_keymap_find_all(C, "NLA Editor", sl->spacetype, 0);
312                                 break;
313                         case SPACE_IMAGE:
314                                 km = WM_keymap_find_all(C, "UV Editor", 0, 0);
315                                 break;
316                         case SPACE_NODE:
317                                 km = WM_keymap_find_all(C, "Node Editor", sl->spacetype, 0);
318                                 break;
319                         case SPACE_SEQ:
320                                 km = WM_keymap_find_all(C, "Sequencer", sl->spacetype, 0);
321                                 break;
322                 }
323         }
324
325         return km;
326 }
327
328 /** \} */