Blender  V2.59
rna_ui.c
Go to the documentation of this file.
00001 /*
00002  * $Id: rna_ui.c 37031 2011-05-31 02:14:25Z campbellbarton $
00003  *
00004  * ***** BEGIN GPL LICENSE BLOCK *****
00005  *
00006  * This program is free software; you can redistribute it and/or
00007  * modify it under the terms of the GNU General Public License
00008  * as published by the Free Software Foundation; either version 2
00009  * of the License, or (at your option) any later version.
00010  *
00011  * This program is distributed in the hope that it will be useful,
00012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014  * GNU General Public License for more details.
00015  *
00016  * You should have received a copy of the GNU General Public License
00017  * along with this program; if not, write to the Free Software Foundation,
00018  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00019  *
00020  * Contributor(s): Blender Foundation (2009)
00021  *
00022  * ***** END GPL LICENSE BLOCK *****
00023  */
00024 
00030 #include <stdlib.h>
00031 
00032 #include "DNA_screen_types.h"
00033 
00034 #include "RNA_define.h"
00035 
00036 #include "rna_internal.h"
00037 #include "RNA_enum_types.h"
00038 
00039 #include "UI_interface.h"
00040 
00041 #include "WM_types.h"
00042 
00043 /* see WM_types.h */
00044 EnumPropertyItem operator_context_items[] = {
00045         {WM_OP_INVOKE_DEFAULT, "INVOKE_DEFAULT", 0, "Invoke Default", ""},
00046         {WM_OP_INVOKE_REGION_WIN, "INVOKE_REGION_WIN", 0, "Invoke Region Window", ""},
00047         {WM_OP_INVOKE_REGION_CHANNELS, "INVOKE_REGION_CHANNELS", 0, "Invoke Region Channels", ""},
00048         {WM_OP_INVOKE_REGION_PREVIEW, "INVOKE_REGION_PREVIEW", 0, "Invoke Region Preview", ""},
00049         {WM_OP_INVOKE_AREA, "INVOKE_AREA", 0, "Invoke Area", ""},
00050         {WM_OP_INVOKE_SCREEN, "INVOKE_SCREEN", 0, "Invoke Screen", ""},
00051         {WM_OP_EXEC_DEFAULT, "EXEC_DEFAULT", 0, "Exec Default", ""},
00052         {WM_OP_EXEC_REGION_WIN, "EXEC_REGION_WIN", 0, "Exec Region Window", ""},
00053         {WM_OP_EXEC_REGION_CHANNELS, "EXEC_REGION_CHANNELS", 0, "Exec Region Channels", ""},
00054         {WM_OP_EXEC_REGION_PREVIEW, "EXEC_REGION_PREVIEW", 0, "Exec Region Preview", ""},
00055         {WM_OP_EXEC_AREA, "EXEC_AREA", 0, "Exec Area", ""},
00056         {WM_OP_EXEC_SCREEN, "EXEC_SCREEN", 0, "Exec Screen", ""},
00057         {0, NULL, 0, NULL, NULL}};
00058 
00059 #ifdef RNA_RUNTIME
00060 
00061 #include "MEM_guardedalloc.h"
00062 
00063 #include "RNA_access.h"
00064 
00065 #include "BLI_dynstr.h"
00066 
00067 #include "BKE_context.h"
00068 #include "BKE_report.h"
00069 #include "BKE_screen.h"
00070 
00071 #include "WM_api.h"
00072 
00073 static ARegionType *region_type_find(ReportList *reports, int space_type, int region_type)
00074 {
00075         SpaceType *st;
00076         ARegionType *art;
00077 
00078         st= BKE_spacetype_from_id(space_type);
00079 
00080         for(art= (st)? st->regiontypes.first: NULL; art; art= art->next) {
00081                 if (art->regionid==region_type)
00082                         break;
00083         }
00084         
00085         /* region type not found? abort */
00086         if (art==NULL) {
00087                 BKE_report(reports, RPT_ERROR, "Region not found in spacetype.");
00088                 return NULL;
00089         }
00090 
00091         return art;
00092 }
00093 
00094 /* Panel */
00095 
00096 static int panel_poll(const bContext *C, PanelType *pt)
00097 {
00098         PointerRNA ptr;
00099         ParameterList list;
00100         FunctionRNA *func;
00101         void *ret;
00102         int visible;
00103 
00104         RNA_pointer_create(NULL, pt->ext.srna, NULL, &ptr); /* dummy */
00105         func= RNA_struct_find_function(&ptr, "poll");
00106 
00107         RNA_parameter_list_create(&list, &ptr, func);
00108         RNA_parameter_set_lookup(&list, "context", &C);
00109         pt->ext.call((bContext *)C, &ptr, func, &list);
00110 
00111         RNA_parameter_get_lookup(&list, "visible", &ret);
00112         visible= *(int*)ret;
00113 
00114         RNA_parameter_list_free(&list);
00115 
00116         return visible;
00117 }
00118 
00119 static void panel_draw(const bContext *C, Panel *pnl)
00120 {
00121         PointerRNA ptr;
00122         ParameterList list;
00123         FunctionRNA *func;
00124 
00125         RNA_pointer_create(&CTX_wm_screen(C)->id, pnl->type->ext.srna, pnl, &ptr);
00126         func= RNA_struct_find_function(&ptr, "draw");
00127 
00128         RNA_parameter_list_create(&list, &ptr, func);
00129         RNA_parameter_set_lookup(&list, "context", &C);
00130         pnl->type->ext.call((bContext *)C, &ptr, func, &list);
00131 
00132         RNA_parameter_list_free(&list);
00133 }
00134 
00135 static void panel_draw_header(const bContext *C, Panel *pnl)
00136 {
00137         PointerRNA ptr;
00138         ParameterList list;
00139         FunctionRNA *func;
00140 
00141         RNA_pointer_create(&CTX_wm_screen(C)->id, pnl->type->ext.srna, pnl, &ptr);
00142         func= RNA_struct_find_function(&ptr, "draw_header");
00143 
00144         RNA_parameter_list_create(&list, &ptr, func);
00145         RNA_parameter_set_lookup(&list, "context", &C);
00146         pnl->type->ext.call((bContext *)C, &ptr, func, &list);
00147 
00148         RNA_parameter_list_free(&list);
00149 }
00150 
00151 static void rna_Panel_unregister(Main *UNUSED(bmain), StructRNA *type)
00152 {
00153         ARegionType *art;
00154         PanelType *pt= RNA_struct_blender_type_get(type);
00155 
00156         if(!pt)
00157                 return;
00158         if(!(art=region_type_find(NULL, pt->space_type, pt->region_type)))
00159                 return;
00160         
00161         RNA_struct_free_extension(type, &pt->ext);
00162 
00163         BLI_freelinkN(&art->paneltypes, pt);
00164         RNA_struct_free(&BLENDER_RNA, type);
00165 
00166         /* update while blender is running */
00167         WM_main_add_notifier(NC_SCREEN|NA_EDITED, NULL);
00168 }
00169 
00170 static StructRNA *rna_Panel_register(Main *bmain, ReportList *reports, void *data, const char *identifier, StructValidateFunc validate, StructCallbackFunc call, StructFreeFunc free)
00171 {
00172         ARegionType *art;
00173         PanelType *pt, dummypt = {NULL};
00174         Panel dummypanel= {NULL};
00175         PointerRNA dummyptr;
00176         int have_function[3];
00177 
00178         /* setup dummy panel & panel type to store static properties in */
00179         dummypanel.type= &dummypt;
00180         RNA_pointer_create(NULL, &RNA_Panel, &dummypanel, &dummyptr);
00181 
00182         /* validate the python class */
00183         if(validate(&dummyptr, data, have_function) != 0)
00184                 return NULL;
00185                 
00186         if(strlen(identifier) >= sizeof(dummypt.idname)) {
00187                 BKE_reportf(reports, RPT_ERROR, "registering panel class: '%s' is too long, maximum length is %d.", identifier, (int)sizeof(dummypt.idname));
00188                 return NULL;
00189         }
00190         
00191         if(!(art=region_type_find(reports, dummypt.space_type, dummypt.region_type)))
00192                 return NULL;
00193 
00194         /* check if we have registered this panel type before, and remove it */
00195         for(pt=art->paneltypes.first; pt; pt=pt->next) {
00196                 if(strcmp(pt->idname, dummypt.idname) == 0) {
00197                         if(pt->ext.srna)
00198                                 rna_Panel_unregister(bmain, pt->ext.srna);
00199                         else
00200                                 BLI_freelinkN(&art->paneltypes, pt);
00201                         break;
00202                 }
00203         }
00204         
00205         /* create a new panel type */
00206         pt= MEM_callocN(sizeof(PanelType), "python buttons panel");
00207         memcpy(pt, &dummypt, sizeof(dummypt));
00208 
00209         pt->ext.srna= RNA_def_struct(&BLENDER_RNA, pt->idname, "Panel"); 
00210         pt->ext.data= data;
00211         pt->ext.call= call;
00212         pt->ext.free= free;
00213         RNA_struct_blender_type_set(pt->ext.srna, pt);
00214         RNA_def_struct_flag(pt->ext.srna, STRUCT_NO_IDPROPERTIES);
00215 
00216         pt->poll= (have_function[0])? panel_poll: NULL;
00217         pt->draw= (have_function[1])? panel_draw: NULL;
00218         pt->draw_header= (have_function[2])? panel_draw_header: NULL;
00219 
00220         /* XXX use "no header" flag for some ordering of panels until we have real panel ordering */
00221         if(pt->flag & PNL_NO_HEADER) {
00222                 PanelType *pth = art->paneltypes.first;
00223                 while(pth && pth->flag & PNL_NO_HEADER)
00224                         pth=pth->next;
00225 
00226                 if(pth)
00227                         BLI_insertlinkbefore(&art->paneltypes, pth, pt);
00228                 else
00229                         BLI_addtail(&art->paneltypes, pt);
00230         }
00231         else
00232                 BLI_addtail(&art->paneltypes, pt);
00233 
00234         /* update while blender is running */
00235         WM_main_add_notifier(NC_SCREEN|NA_EDITED, NULL);
00236         
00237         return pt->ext.srna;
00238 }
00239 
00240 static StructRNA* rna_Panel_refine(PointerRNA *ptr)
00241 {
00242         Panel *hdr= (Panel*)ptr->data;
00243         return (hdr->type && hdr->type->ext.srna)? hdr->type->ext.srna: &RNA_Panel;
00244 }
00245 
00246 /* Header */
00247 
00248 static void header_draw(const bContext *C, Header *hdr)
00249 {
00250         PointerRNA htr;
00251         ParameterList list;
00252         FunctionRNA *func;
00253 
00254         RNA_pointer_create(&CTX_wm_screen(C)->id, hdr->type->ext.srna, hdr, &htr);
00255         func= RNA_struct_find_function(&htr, "draw");
00256 
00257         RNA_parameter_list_create(&list, &htr, func);
00258         RNA_parameter_set_lookup(&list, "context", &C);
00259         hdr->type->ext.call((bContext *)C, &htr, func, &list);
00260 
00261         RNA_parameter_list_free(&list);
00262 }
00263 
00264 static void rna_Header_unregister(Main *UNUSED(bmain), StructRNA *type)
00265 {
00266         ARegionType *art;
00267         HeaderType *ht= RNA_struct_blender_type_get(type);
00268 
00269         if(!ht)
00270                 return;
00271         if(!(art=region_type_find(NULL, ht->space_type, RGN_TYPE_HEADER)))
00272                 return;
00273         
00274         RNA_struct_free_extension(type, &ht->ext);
00275 
00276         BLI_freelinkN(&art->headertypes, ht);
00277         RNA_struct_free(&BLENDER_RNA, type);
00278 
00279         /* update while blender is running */
00280         WM_main_add_notifier(NC_SCREEN|NA_EDITED, NULL);
00281 }
00282 
00283 static StructRNA *rna_Header_register(Main *bmain, ReportList *reports, void *data, const char *identifier, StructValidateFunc validate, StructCallbackFunc call, StructFreeFunc free)
00284 {
00285         ARegionType *art;
00286         HeaderType *ht, dummyht = {NULL};
00287         Header dummyheader= {NULL};
00288         PointerRNA dummyhtr;
00289         int have_function[1];
00290 
00291         /* setup dummy header & header type to store static properties in */
00292         dummyheader.type= &dummyht;
00293         RNA_pointer_create(NULL, &RNA_Header, &dummyheader, &dummyhtr);
00294 
00295         /* validate the python class */
00296         if(validate(&dummyhtr, data, have_function) != 0)
00297                 return NULL;
00298 
00299         if(strlen(identifier) >= sizeof(dummyht.idname)) {
00300                 BKE_reportf(reports, RPT_ERROR, "registering header class: '%s' is too long, maximum length is %d.", identifier, (int)sizeof(dummyht.idname));
00301                 return NULL;
00302         }
00303 
00304         if(!(art=region_type_find(reports, dummyht.space_type, RGN_TYPE_HEADER)))
00305                 return NULL;
00306 
00307         /* check if we have registered this header type before, and remove it */
00308         for(ht=art->headertypes.first; ht; ht=ht->next) {
00309                 if(strcmp(ht->idname, dummyht.idname) == 0) {
00310                         if(ht->ext.srna)
00311                                 rna_Header_unregister(bmain, ht->ext.srna);
00312                         break;
00313                 }
00314         }
00315         
00316         /* create a new header type */
00317         ht= MEM_callocN(sizeof(HeaderType), "python buttons header");
00318         memcpy(ht, &dummyht, sizeof(dummyht));
00319 
00320         ht->ext.srna= RNA_def_struct(&BLENDER_RNA, ht->idname, "Header"); 
00321         ht->ext.data= data;
00322         ht->ext.call= call;
00323         ht->ext.free= free;
00324         RNA_struct_blender_type_set(ht->ext.srna, ht);
00325 
00326         ht->draw= (have_function[0])? header_draw: NULL;
00327 
00328         BLI_addtail(&art->headertypes, ht);
00329 
00330         /* update while blender is running */
00331         WM_main_add_notifier(NC_SCREEN|NA_EDITED, NULL);
00332         
00333         return ht->ext.srna;
00334 }
00335 
00336 static StructRNA* rna_Header_refine(PointerRNA *htr)
00337 {
00338         Header *hdr= (Header*)htr->data;
00339         return (hdr->type && hdr->type->ext.srna)? hdr->type->ext.srna: &RNA_Header;
00340 }
00341 
00342 /* Menu */
00343 
00344 static int menu_poll(const bContext *C, MenuType *pt)
00345 {
00346         PointerRNA ptr;
00347         ParameterList list;
00348         FunctionRNA *func;
00349         void *ret;
00350         int visible;
00351 
00352         RNA_pointer_create(NULL, pt->ext.srna, NULL, &ptr); /* dummy */
00353         func= RNA_struct_find_function(&ptr, "poll");
00354 
00355         RNA_parameter_list_create(&list, &ptr, func);
00356         RNA_parameter_set_lookup(&list, "context", &C);
00357         pt->ext.call((bContext *)C, &ptr, func, &list);
00358 
00359         RNA_parameter_get_lookup(&list, "visible", &ret);
00360         visible= *(int*)ret;
00361 
00362         RNA_parameter_list_free(&list);
00363 
00364         return visible;
00365 }
00366 
00367 static void menu_draw(const bContext *C, Menu *hdr)
00368 {
00369         PointerRNA mtr;
00370         ParameterList list;
00371         FunctionRNA *func;
00372 
00373         RNA_pointer_create(&CTX_wm_screen(C)->id, hdr->type->ext.srna, hdr, &mtr);
00374         func= RNA_struct_find_function(&mtr, "draw");
00375 
00376         RNA_parameter_list_create(&list, &mtr, func);
00377         RNA_parameter_set_lookup(&list, "context", &C);
00378         hdr->type->ext.call((bContext *)C, &mtr, func, &list);
00379 
00380         RNA_parameter_list_free(&list);
00381 }
00382 
00383 static void rna_Menu_unregister(Main *UNUSED(bmain), StructRNA *type)
00384 {
00385         MenuType *mt= RNA_struct_blender_type_get(type);
00386 
00387         if(!mt)
00388                 return;
00389         
00390         RNA_struct_free_extension(type, &mt->ext);
00391 
00392         WM_menutype_freelink(mt);
00393 
00394         RNA_struct_free(&BLENDER_RNA, type);
00395 
00396         /* update while blender is running */
00397         WM_main_add_notifier(NC_SCREEN|NA_EDITED, NULL);
00398 }
00399 
00400 static StructRNA *rna_Menu_register(Main *bmain, ReportList *reports, void *data, const char *identifier, StructValidateFunc validate, StructCallbackFunc call, StructFreeFunc free)
00401 {
00402         MenuType *mt, dummymt = {NULL};
00403         Menu dummymenu= {NULL};
00404         PointerRNA dummymtr;
00405         int have_function[2];
00406 
00407         /* setup dummy menu & menu type to store static properties in */
00408         dummymenu.type= &dummymt;
00409         RNA_pointer_create(NULL, &RNA_Menu, &dummymenu, &dummymtr);
00410 
00411         /* validate the python class */
00412         if(validate(&dummymtr, data, have_function) != 0)
00413                 return NULL;
00414         
00415         if(strlen(identifier) >= sizeof(dummymt.idname)) {
00416                 BKE_reportf(reports, RPT_ERROR, "registering menu class: '%s' is too long, maximum length is %d.", identifier, (int)sizeof(dummymt.idname));
00417                 return NULL;
00418         }
00419 
00420         /* check if we have registered this menu type before, and remove it */
00421         mt= WM_menutype_find(dummymt.idname, TRUE);
00422         if(mt && mt->ext.srna)
00423                 rna_Menu_unregister(bmain, mt->ext.srna);
00424         
00425         /* create a new menu type */
00426         mt= MEM_callocN(sizeof(MenuType), "python buttons menu");
00427         memcpy(mt, &dummymt, sizeof(dummymt));
00428 
00429         mt->ext.srna= RNA_def_struct(&BLENDER_RNA, mt->idname, "Menu"); 
00430         mt->ext.data= data;
00431         mt->ext.call= call;
00432         mt->ext.free= free;
00433         RNA_struct_blender_type_set(mt->ext.srna, mt);
00434         RNA_def_struct_flag(mt->ext.srna, STRUCT_NO_IDPROPERTIES);
00435 
00436         mt->poll= (have_function[0])? menu_poll: NULL;
00437         mt->draw= (have_function[1])? menu_draw: NULL;
00438 
00439         WM_menutype_add(mt);
00440 
00441         /* update while blender is running */
00442         WM_main_add_notifier(NC_SCREEN|NA_EDITED, NULL);
00443         
00444         return mt->ext.srna;
00445 }
00446 
00447 static StructRNA* rna_Menu_refine(PointerRNA *mtr)
00448 {
00449         Menu *hdr= (Menu*)mtr->data;
00450         return (hdr->type && hdr->type->ext.srna)? hdr->type->ext.srna: &RNA_Menu;
00451 }
00452 
00453 static int rna_UILayout_active_get(PointerRNA *ptr)
00454 {
00455         return uiLayoutGetActive(ptr->data);
00456 }
00457 
00458 static void rna_UILayout_active_set(PointerRNA *ptr, int value)
00459 {
00460         uiLayoutSetActive(ptr->data, value);
00461 }
00462 
00463 static int rna_UILayout_alert_get(PointerRNA *ptr)
00464 {
00465         return uiLayoutGetRedAlert(ptr->data);
00466 }
00467 
00468 static void rna_UILayout_alert_set(PointerRNA *ptr, int value)
00469 {
00470         uiLayoutSetRedAlert(ptr->data, value);
00471 }
00472 
00473 static void rna_UILayout_op_context_set(PointerRNA *ptr, int value)
00474 {
00475         uiLayoutSetOperatorContext(ptr->data, value);
00476 }
00477 
00478 static int rna_UILayout_op_context_get(PointerRNA *ptr)
00479 {
00480         return uiLayoutGetOperatorContext(ptr->data);
00481 }
00482 
00483 static int rna_UILayout_enabled_get(PointerRNA *ptr)
00484 {
00485         return uiLayoutGetEnabled(ptr->data);
00486 }
00487 
00488 static void rna_UILayout_enabled_set(PointerRNA *ptr, int value)
00489 {
00490         uiLayoutSetEnabled(ptr->data, value);
00491 }
00492 
00493 #if 0
00494 static int rna_UILayout_red_alert_get(PointerRNA *ptr)
00495 {
00496         return uiLayoutGetRedAlert(ptr->data);
00497 }
00498 
00499 static void rna_UILayout_red_alert_set(PointerRNA *ptr, int value)
00500 {
00501         uiLayoutSetRedAlert(ptr->data, value);
00502 }
00503 
00504 static int rna_UILayout_keep_aspect_get(PointerRNA *ptr)
00505 {
00506         return uiLayoutGetKeepAspect(ptr->data);
00507 }
00508 
00509 static void rna_UILayout_keep_aspect_set(PointerRNA *ptr, int value)
00510 {
00511         uiLayoutSetKeepAspect(ptr->data, value);
00512 }
00513 #endif
00514 
00515 static int rna_UILayout_alignment_get(PointerRNA *ptr)
00516 {
00517         return uiLayoutGetAlignment(ptr->data);
00518 }
00519 
00520 static void rna_UILayout_alignment_set(PointerRNA *ptr, int value)
00521 {
00522         uiLayoutSetAlignment(ptr->data, value);
00523 }
00524 
00525 static float rna_UILayout_scale_x_get(PointerRNA *ptr)
00526 {
00527         return uiLayoutGetScaleX(ptr->data);
00528 }
00529 
00530 static void rna_UILayout_scale_x_set(PointerRNA *ptr, float value)
00531 {
00532         uiLayoutSetScaleX(ptr->data, value);
00533 }
00534 
00535 static float rna_UILayout_scale_y_get(PointerRNA *ptr)
00536 {
00537         return uiLayoutGetScaleY(ptr->data);
00538 }
00539 
00540 static void rna_UILayout_scale_y_set(PointerRNA *ptr, float value)
00541 {
00542         uiLayoutSetScaleY(ptr->data, value);
00543 }
00544 
00545 #else // RNA_RUNTIME
00546 
00547 static void rna_def_ui_layout(BlenderRNA *brna)
00548 {
00549         StructRNA *srna;
00550         PropertyRNA *prop;
00551 
00552         static EnumPropertyItem alignment_items[] = {
00553                 {UI_LAYOUT_ALIGN_EXPAND, "EXPAND", 0, "Expand", ""},
00554                 {UI_LAYOUT_ALIGN_LEFT, "LEFT", 0, "Left", ""},
00555                 {UI_LAYOUT_ALIGN_CENTER, "CENTER", 0, "Center", ""},
00556                 {UI_LAYOUT_ALIGN_RIGHT, "RIGHT", 0, "Right", ""},
00557                 {0, NULL, 0, NULL, NULL}};
00558         
00559         /* layout */
00560 
00561         srna= RNA_def_struct(brna, "UILayout", NULL);
00562         RNA_def_struct_sdna(srna, "uiLayout");
00563         RNA_def_struct_ui_text(srna, "UI Layout", "User interface layout in a panel or header");
00564 
00565         prop= RNA_def_property(srna, "active", PROP_BOOLEAN, PROP_NONE);
00566         RNA_def_property_boolean_funcs(prop, "rna_UILayout_active_get", "rna_UILayout_active_set");
00567         
00568         prop= RNA_def_property(srna, "operator_context", PROP_ENUM, PROP_NONE);
00569         RNA_def_property_enum_items(prop, operator_context_items);
00570         RNA_def_property_enum_funcs(prop, "rna_UILayout_op_context_get", "rna_UILayout_op_context_set", NULL);
00571         
00572         prop= RNA_def_property(srna, "enabled", PROP_BOOLEAN, PROP_NONE);
00573         RNA_def_property_boolean_funcs(prop, "rna_UILayout_enabled_get", "rna_UILayout_enabled_set");
00574         RNA_def_property_ui_text(prop, "Enabled", "When false, this (sub)layout is greyed out.");
00575         
00576         prop= RNA_def_property(srna, "alert", PROP_BOOLEAN, PROP_NONE);
00577         RNA_def_property_boolean_funcs(prop, "rna_UILayout_alert_get", "rna_UILayout_alert_set");
00578 
00579         prop= RNA_def_property(srna, "alignment", PROP_ENUM, PROP_NONE);
00580         RNA_def_property_enum_items(prop, alignment_items);
00581         RNA_def_property_enum_funcs(prop, "rna_UILayout_alignment_get", "rna_UILayout_alignment_set", NULL);
00582 
00583 #if 0
00584         prop= RNA_def_property(srna, "keep_aspect", PROP_BOOLEAN, PROP_NONE);
00585         RNA_def_property_boolean_funcs(prop, "rna_UILayout_keep_aspect_get", "rna_UILayout_keep_aspect_set");
00586 #endif
00587 
00588         prop= RNA_def_property(srna, "scale_x", PROP_FLOAT, PROP_UNSIGNED);
00589         RNA_def_property_float_funcs(prop, "rna_UILayout_scale_x_get", "rna_UILayout_scale_x_set", NULL);
00590         RNA_def_property_ui_text(prop, "Scale X", "Scale factor along the X for items in this (sub)layout.");
00591         
00592         prop= RNA_def_property(srna, "scale_y", PROP_FLOAT, PROP_UNSIGNED);
00593         RNA_def_property_float_funcs(prop, "rna_UILayout_scale_y_get", "rna_UILayout_scale_y_set", NULL);
00594         RNA_def_property_ui_text(prop, "Scale Y", "Scale factor along the Y for items in this (sub)layout.");
00595         RNA_api_ui_layout(srna);
00596 }
00597 
00598 static void rna_def_panel(BlenderRNA *brna)
00599 {
00600         StructRNA *srna;
00601         PropertyRNA *prop;
00602         PropertyRNA *parm;
00603         FunctionRNA *func;
00604         
00605         static EnumPropertyItem panel_flag_items[] = {
00606                         {PNL_DEFAULT_CLOSED, "DEFAULT_CLOSED", 0, "Default Closed", "Defines if the panel has to be open or collapsed at the time of its creation."},
00607                         {PNL_NO_HEADER, "HIDE_HEADER", 0, "Show Header", "If set to True, the panel shows a header, which contains a clickable arrow to collapse the panel and the label (see bl_label)."},
00608                         {0, NULL, 0, NULL, NULL}};
00609         
00610         srna= RNA_def_struct(brna, "Panel", NULL);
00611         RNA_def_struct_ui_text(srna, "Panel", "Panel containing UI elements");
00612         RNA_def_struct_sdna(srna, "Panel");
00613         RNA_def_struct_refine_func(srna, "rna_Panel_refine");
00614         RNA_def_struct_register_funcs(srna, "rna_Panel_register", "rna_Panel_unregister", NULL);
00615 
00616         /* poll */
00617         func= RNA_def_function(srna, "poll", NULL);
00618         RNA_def_function_ui_description(func, "If this method returns a non-null output, then the panel can be drawn.");
00619         RNA_def_function_flag(func, FUNC_NO_SELF|FUNC_REGISTER_OPTIONAL);
00620         RNA_def_function_return(func, RNA_def_boolean(func, "visible", 1, "", ""));
00621         parm= RNA_def_pointer(func, "context", "Context", "", "");
00622         RNA_def_property_flag(parm, PROP_REQUIRED|PROP_NEVER_NULL);
00623 
00624         /* draw */
00625         func= RNA_def_function(srna, "draw", NULL);
00626         RNA_def_function_ui_description(func, "Draw UI elements into the panel UI layout.");
00627         RNA_def_function_flag(func, FUNC_REGISTER);
00628         parm= RNA_def_pointer(func, "context", "Context", "", "");
00629         RNA_def_property_flag(parm, PROP_REQUIRED|PROP_NEVER_NULL);
00630 
00631         func= RNA_def_function(srna, "draw_header", NULL);
00632         RNA_def_function_ui_description(func, "Draw UI elements into the panel's header UI layout.");
00633         RNA_def_function_flag(func, FUNC_REGISTER);
00634         parm= RNA_def_pointer(func, "context", "Context", "", "");
00635         RNA_def_property_flag(parm, PROP_REQUIRED|PROP_NEVER_NULL);
00636 
00637         prop= RNA_def_property(srna, "layout", PROP_POINTER, PROP_NONE);
00638         RNA_def_property_struct_type(prop, "UILayout");
00639         RNA_def_property_ui_text(prop, "Layout", "Defines the structure of the panel in the UI.");
00640         
00641         prop= RNA_def_property(srna, "text", PROP_STRING, PROP_NONE);
00642         RNA_def_property_string_sdna(prop, NULL, "drawname");
00643         RNA_def_property_ui_text(prop, "Text", "XXX todo");
00644         
00645         /* registration */
00646         prop= RNA_def_property(srna, "bl_idname", PROP_STRING, PROP_NONE);
00647         RNA_def_property_string_sdna(prop, NULL, "type->idname");
00648         RNA_def_property_flag(prop, PROP_REGISTER|PROP_NEVER_CLAMP);
00649         RNA_def_property_ui_text(prop, "ID Name", "If this is set, the panel gets a custom ID, otherwise it takes the name of the class used to define the panel. For example, if the class name is \"OBJECT_PT_hello\", and bl_idname is not set by the script, then bl_idname = \"OBJECT_PT_hello\"");
00650         
00651         prop= RNA_def_property(srna, "bl_label", PROP_STRING, PROP_NONE);
00652         RNA_def_property_string_sdna(prop, NULL, "type->label");
00653         RNA_def_property_flag(prop, PROP_REGISTER);
00654         RNA_def_property_ui_text(prop, "Label", "The panel label, shows up in the panel header at the right of the triangle used to collapse the panel.");
00655         
00656         prop= RNA_def_property(srna, "bl_space_type", PROP_ENUM, PROP_NONE);
00657         RNA_def_property_enum_sdna(prop, NULL, "type->space_type");
00658         RNA_def_property_enum_items(prop, space_type_items);
00659         RNA_def_property_flag(prop, PROP_REGISTER);
00660         RNA_def_property_ui_text(prop, "Space type", "The space where the panel is going to be used in.");
00661         
00662         prop= RNA_def_property(srna, "bl_region_type", PROP_ENUM, PROP_NONE);
00663         RNA_def_property_enum_sdna(prop, NULL, "type->region_type");
00664         RNA_def_property_enum_items(prop, region_type_items);
00665         RNA_def_property_flag(prop, PROP_REGISTER);
00666         RNA_def_property_ui_text(prop, "Region Type", "The region where the panel is going to be used in.");
00667 
00668         prop= RNA_def_property(srna, "bl_context", PROP_STRING, PROP_NONE);
00669         RNA_def_property_string_sdna(prop, NULL, "type->context");
00670         RNA_def_property_flag(prop, PROP_REGISTER_OPTIONAL); /* should this be optional? - Campbell */
00671         RNA_def_property_ui_text(prop, "Context", "The context in which the panel belongs to. (TODO: explain the possible combinations bl_context/bl_region_type/bl_space_type)");
00672         
00673         prop= RNA_def_property(srna, "bl_options", PROP_ENUM, PROP_NONE);
00674         RNA_def_property_enum_sdna(prop, NULL, "type->flag");
00675         RNA_def_property_enum_items(prop, panel_flag_items);
00676         RNA_def_property_flag(prop, PROP_REGISTER_OPTIONAL|PROP_ENUM_FLAG);
00677         RNA_def_property_ui_text(prop, "Options",  "Options for this panel type");
00678 }
00679 
00680 static void rna_def_header(BlenderRNA *brna)
00681 {
00682         StructRNA *srna;
00683         PropertyRNA *prop;
00684         PropertyRNA *parm;
00685         FunctionRNA *func;
00686         
00687         srna= RNA_def_struct(brna, "Header", NULL);
00688         RNA_def_struct_ui_text(srna, "Header", "Editor header containing UI elements.");
00689         RNA_def_struct_sdna(srna, "Header");
00690         RNA_def_struct_refine_func(srna, "rna_Header_refine");
00691         RNA_def_struct_register_funcs(srna, "rna_Header_register", "rna_Header_unregister", NULL);
00692 
00693         /* draw */
00694         func= RNA_def_function(srna, "draw", NULL);
00695         RNA_def_function_ui_description(func, "Draw UI elements into the header UI layout.");
00696         RNA_def_function_flag(func, FUNC_REGISTER);
00697         parm= RNA_def_pointer(func, "context", "Context", "", "");
00698         RNA_def_property_flag(parm, PROP_REQUIRED);
00699 
00700         RNA_define_verify_sdna(0); // not in sdna
00701 
00702         prop= RNA_def_property(srna, "layout", PROP_POINTER, PROP_NONE);
00703         RNA_def_property_pointer_sdna(prop, NULL, "layout");
00704         RNA_def_property_struct_type(prop, "UILayout");
00705         RNA_def_property_ui_text(prop, "Layout", "Defines the structure of the header in the UI.");
00706 
00707         /* registration */
00708         prop= RNA_def_property(srna, "bl_idname", PROP_STRING, PROP_NONE);
00709         RNA_def_property_string_sdna(prop, NULL, "type->idname");
00710         RNA_def_property_flag(prop, PROP_REGISTER|PROP_NEVER_CLAMP);
00711         RNA_def_property_ui_text(prop, "ID Name", "If this is set, the header gets a custom ID, otherwise it takes the name of the class used to define the panel. For example, if the class name is \"OBJECT_HT_hello\", and bl_idname is not set by the script, then bl_idname = \"OBJECT_HT_hello\"");
00712 
00713         prop= RNA_def_property(srna, "bl_space_type", PROP_ENUM, PROP_NONE);
00714         RNA_def_property_enum_sdna(prop, NULL, "type->space_type");
00715         RNA_def_property_enum_items(prop, space_type_items);
00716         RNA_def_property_flag(prop, PROP_REGISTER);
00717         RNA_def_property_ui_text(prop, "Space type", "The space where the header is going to be used in.");
00718 
00719         RNA_define_verify_sdna(1);
00720 }
00721 
00722 static void rna_def_menu(BlenderRNA *brna)
00723 {
00724         StructRNA *srna;
00725         PropertyRNA *prop;
00726         PropertyRNA *parm;
00727         FunctionRNA *func;
00728         
00729         srna= RNA_def_struct(brna, "Menu", NULL);
00730         RNA_def_struct_ui_text(srna, "Menu", "Editor menu containing buttons");
00731         RNA_def_struct_sdna(srna, "Menu");
00732         RNA_def_struct_refine_func(srna, "rna_Menu_refine");
00733         RNA_def_struct_register_funcs(srna, "rna_Menu_register", "rna_Menu_unregister", NULL);
00734 
00735         /* poll */
00736         func= RNA_def_function(srna, "poll", NULL);
00737         RNA_def_function_ui_description(func, "If this method returns a non-null output, then the menu can be drawn.");
00738         RNA_def_function_flag(func, FUNC_NO_SELF|FUNC_REGISTER_OPTIONAL);
00739         RNA_def_function_return(func, RNA_def_boolean(func, "visible", 1, "", ""));
00740         parm= RNA_def_pointer(func, "context", "Context", "", "");
00741         RNA_def_property_flag(parm, PROP_REQUIRED);
00742 
00743         /* draw */
00744         func= RNA_def_function(srna, "draw", NULL);
00745         RNA_def_function_ui_description(func, "Draw UI elements into the menu UI layout.");
00746         RNA_def_function_flag(func, FUNC_REGISTER);
00747         parm= RNA_def_pointer(func, "context", "Context", "", "");
00748         RNA_def_property_flag(parm, PROP_REQUIRED);
00749 
00750         RNA_define_verify_sdna(0); // not in sdna
00751 
00752         prop= RNA_def_property(srna, "layout", PROP_POINTER, PROP_NONE);
00753         RNA_def_property_pointer_sdna(prop, NULL, "layout");
00754         RNA_def_property_struct_type(prop, "UILayout");
00755         RNA_def_property_ui_text(prop, "Layout", "Defines the structure of the menu in the UI.");
00756 
00757         /* registration */
00758         prop= RNA_def_property(srna, "bl_idname", PROP_STRING, PROP_NONE);
00759         RNA_def_property_string_sdna(prop, NULL, "type->idname");
00760         RNA_def_property_flag(prop, PROP_REGISTER|PROP_NEVER_CLAMP);
00761         RNA_def_property_ui_text(prop, "ID Name", "If this is set, the menu gets a custom ID, otherwise it takes the name of the class used to define the panel. For example, if the class name is \"OBJECT_MT_hello\", and bl_idname is not set by the script, then bl_idname = \"OBJECT_MT_hello\"");
00762 
00763         prop= RNA_def_property(srna, "bl_label", PROP_STRING, PROP_NONE);
00764         RNA_def_property_string_sdna(prop, NULL, "type->label");
00765         RNA_def_property_flag(prop, PROP_REGISTER);
00766         RNA_def_property_ui_text(prop, "Label", "The menu label");
00767 
00768         RNA_define_verify_sdna(1);
00769 }
00770 
00771 void RNA_def_ui(BlenderRNA *brna)
00772 {
00773         rna_def_ui_layout(brna);
00774         rna_def_panel(brna);
00775         rna_def_header(brna);
00776         rna_def_menu(brna);
00777 }
00778 
00779 #endif // RNA_RUNTIME
00780