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:
authorAndrea Weikert <elubie@gmx.net>2007-09-02 21:25:03 +0400
committerAndrea Weikert <elubie@gmx.net>2007-09-02 21:25:03 +0400
commit356ab943736e8a2434a8ff5845873482597ba5e2 (patch)
tree910356ace904dc4f11f1daf15330bb0827934f5b /source/blender
parent22c23fb04f7f1297b971f03d69b8b04b7dd9caa4 (diff)
== imagebrowser ==
Initial commit of imagebrowser in trunk. BIG COMMIT! Main changes: * completely reworked imasel space * creation and storage of the preview images for materials, textures, world and lamp * thumbnails of images and movie files when browsing in the file system * loading previews from external .blend when linking or appending * thumbnail caching according to the Thumbnail Managing Standard: http://jens.triq.net/thumbnail-spec/ * for now just kept imasel access mostly as old imgbrowser (CTRL+F4, CTRL+F1) a bit hidden still. * filtering of file types (images, movies, .blend, py,...) * preliminary managing of bookmarks ('B' button to add, XKEY while bookmark active to delete) More detailed info which will be updated here: http://wiki.blender.org/index.php/User:Elubie/PreviewImageBrowser Places that need special review (and probably fixes): * BLO_blendhandle_get_previews in readblenentry * readfile.c: do_version and refactorings of do_library_append * UI integration TODO and known issues still: * Accented characters do not display correctly with international fonts * Crash was reported when browsing in directory with movie files * Bookmark management still needs some UI work (second scrollbar?), feedback here is welcome! Credits: Samir Bharadwaj (samirbharadwaj@yahoo.com) for the icon images. Many thanks to everyone who gave feedback and helped so far!
Diffstat (limited to 'source/blender')
-rw-r--r--source/blender/blenkernel/BKE_icons.h75
-rw-r--r--source/blender/blenkernel/bad_level_call_stubs/stubs.c4
-rw-r--r--source/blender/blenkernel/intern/icons.c169
-rw-r--r--source/blender/blenkernel/intern/image.c11
-rw-r--r--source/blender/blenkernel/intern/material.c5
-rw-r--r--source/blender/blenkernel/intern/object.c7
-rw-r--r--source/blender/blenkernel/intern/texture.c5
-rw-r--r--source/blender/blenkernel/intern/world.c7
-rw-r--r--source/blender/blenlib/BLI_blenlib.h5
-rw-r--r--source/blender/blenlib/BLI_storage_types.h3
-rw-r--r--source/blender/blenlib/intern/util.c32
-rw-r--r--source/blender/blenloader/BLO_readfile.h19
-rw-r--r--source/blender/blenloader/intern/readblenentry.c66
-rw-r--r--source/blender/blenloader/intern/readfile.c144
-rw-r--r--source/blender/blenloader/intern/writefile.c42
-rw-r--r--source/blender/imbuf/IMB_imbuf.h7
-rw-r--r--source/blender/imbuf/IMB_imbuf_types.h4
-rw-r--r--source/blender/imbuf/IMB_thumbs.h73
-rw-r--r--source/blender/imbuf/intern/IMB_imginfo.h78
-rw-r--r--source/blender/imbuf/intern/allocimbuf.c5
-rw-r--r--source/blender/imbuf/intern/anim.c12
-rw-r--r--source/blender/imbuf/intern/imginfo.c108
-rw-r--r--source/blender/imbuf/intern/md5.c360
-rw-r--r--source/blender/imbuf/intern/md5.h115
-rw-r--r--source/blender/imbuf/intern/png.c38
-rw-r--r--source/blender/imbuf/intern/thumbs.c457
-rw-r--r--source/blender/include/BIF_filelist.h87
-rw-r--r--source/blender/include/BIF_fsmenu.h7
-rw-r--r--source/blender/include/BIF_imasel.h25
-rw-r--r--source/blender/include/BIF_interface_icons.h3
-rw-r--r--source/blender/include/BIF_resources.h2
-rw-r--r--source/blender/include/BIF_space.h3
-rw-r--r--source/blender/include/BSE_drawimasel.h35
-rw-r--r--source/blender/include/BSE_filesel.h2
-rw-r--r--source/blender/include/blendef.h5
-rw-r--r--source/blender/include/datatoc.h3
-rw-r--r--source/blender/include/interface.h2
-rw-r--r--source/blender/makesdna/DNA_ID.h12
-rw-r--r--source/blender/makesdna/DNA_image_types.h5
-rw-r--r--source/blender/makesdna/DNA_lamp_types.h3
-rw-r--r--source/blender/makesdna/DNA_material_types.h3
-rw-r--r--source/blender/makesdna/DNA_space_types.h132
-rw-r--r--source/blender/makesdna/DNA_texture_types.h3
-rw-r--r--source/blender/makesdna/DNA_userdef_types.h1
-rw-r--r--source/blender/makesdna/DNA_world_types.h3
-rw-r--r--source/blender/python/api2_2x/Window.c1
-rw-r--r--source/blender/quicktime/apple/quicktime_import.c19
-rw-r--r--source/blender/src/buttons_scene.c1
-rw-r--r--source/blender/src/buttons_shading.c8
-rw-r--r--source/blender/src/drawimasel.c1338
-rw-r--r--source/blender/src/drawnode.c35
-rw-r--r--source/blender/src/editimasel.c1297
-rw-r--r--source/blender/src/editscreen.c5
-rw-r--r--source/blender/src/editsima.c1
-rw-r--r--source/blender/src/filelist.c1093
-rw-r--r--source/blender/src/filesel.c191
-rw-r--r--source/blender/src/fsmenu.c260
-rw-r--r--source/blender/src/glutil.c21
-rw-r--r--source/blender/src/header_imasel.c114
-rw-r--r--source/blender/src/header_info.c5
-rw-r--r--source/blender/src/headerbuttons.c7
-rw-r--r--source/blender/src/imasel.c861
-rw-r--r--source/blender/src/interface_draw.c30
-rw-r--r--source/blender/src/interface_icons.c320
-rw-r--r--source/blender/src/prvicons.c436
-rw-r--r--source/blender/src/resources.c17
-rw-r--r--source/blender/src/space.c130
-rw-r--r--source/blender/src/toets.c14
-rw-r--r--source/blender/src/usiblender.c23
69 files changed, 5802 insertions, 2612 deletions
diff --git a/source/blender/blenkernel/BKE_icons.h b/source/blender/blenkernel/BKE_icons.h
index 315c7dc7a53..737adea78be 100644
--- a/source/blender/blenkernel/BKE_icons.h
+++ b/source/blender/blenkernel/BKE_icons.h
@@ -1,34 +1,32 @@
/**
- * $Id$
- *
- * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
- *
- * 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. The Blender
- * Foundation also sells licenses for use in proprietary software under
- * the Blender License. See http://www.blender.org/BL/ for information
- * about this.
- *
- * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
- *
- * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
- * All rights reserved.
- *
- * The Original Code is: all of this file.
- *
- * Contributor(s): none yet.
- *
- * ***** END GPL/BL DUAL LICENSE BLOCK *****
- */
+* $Id$
+*
+* ***** BEGIN GPL LICENSE BLOCK *****
+*
+* 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+*
+* The Original Code is Copyright (C) 2006-2007 Blender Foundation.
+* All rights reserved.
+*
+* The Original Code is: all of this file.
+*
+* Contributor(s): none yet.
+*
+* ***** END GPL LICENSE BLOCK *****
+*
+*/
#ifndef BKE_ICONS_H
#define BKE_ICONS_H
@@ -44,12 +42,13 @@ struct Icon
void *drawinfo;
void *obj;
short type;
- short changed;
DrawInfoFreeFP drawinfo_free;
};
typedef struct Icon Icon;
+struct PreviewImage;
+
void BKE_icons_init(int first_dyn_id);
/* return icon id for library object or create new icon if not found */
@@ -71,5 +70,19 @@ void BKE_icon_changed(int icon_id);
/* free all icons */
void BKE_icons_free();
+/* free the preview image */
+void BKE_previewimg_free(struct PreviewImage **prv);
+
+/* free the preview image belonging to the id */
+void BKE_previewimg_free_id(ID *id);
+
+/* create a new preview image */
+struct PreviewImage* BKE_previewimg_create() ;
+
+/* create a copy of the preview image */
+struct PreviewImage* BKE_previewimg_copy(struct PreviewImage *prv);
+
+/* retrieve existing or create new preview image */
+PreviewImage* BKE_previewimg_get(ID *id);
#endif /* BKE_ICONS_H */
diff --git a/source/blender/blenkernel/bad_level_call_stubs/stubs.c b/source/blender/blenkernel/bad_level_call_stubs/stubs.c
index 4521f1d1dea..04fac832cc4 100644
--- a/source/blender/blenkernel/bad_level_call_stubs/stubs.c
+++ b/source/blender/blenkernel/bad_level_call_stubs/stubs.c
@@ -324,3 +324,7 @@ void antialias_tagbuf(int xsize, int ysize, char *rectmove) {}
void ibuf_sample(struct ImBuf *ibuf, float fx, float fy, float dx, float dy, float *result) {}
void update_for_newframe() {}
+
+struct FileList;
+void BIF_filelist_freelib(struct FileList* filelist) {};
+
diff --git a/source/blender/blenkernel/intern/icons.c b/source/blender/blenkernel/intern/icons.c
index ee37a4ec9f9..f144d2badd1 100644
--- a/source/blender/blenkernel/intern/icons.c
+++ b/source/blender/blenkernel/intern/icons.c
@@ -1,34 +1,32 @@
/**
- * $Id$
- *
- * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
- *
- * 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. The Blender
- * Foundation also sells licenses for use in proprietary software under
- * the Blender License. See http://www.blender.org/BL/ for information
- * about this.
- *
- * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
- *
- * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
- * All rights reserved.
- *
- * The Original Code is: all of this file.
- *
- * Contributor(s): none yet.
- *
- * ***** END GPL/BL DUAL LICENSE BLOCK *****
- */
+* $Id$
+*
+* ***** BEGIN GPL LICENSE BLOCK *****
+*
+* 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+*
+* The Original Code is Copyright (C) 2006-2007 Blender Foundation.
+* All rights reserved.
+*
+* The Original Code is: all of this file.
+*
+* Contributor(s): none yet.
+*
+* ***** END GPL LICENSE BLOCK *****
+*
+*/
#include <math.h>
#include <stdlib.h>
@@ -41,6 +39,11 @@
#include "MEM_guardedalloc.h"
#include "DNA_ID.h"
+#include "DNA_image_types.h"
+#include "DNA_lamp_types.h"
+#include "DNA_material_types.h"
+#include "DNA_texture_types.h"
+#include "DNA_world_types.h"
#include "BLI_ghash.h"
@@ -111,6 +114,101 @@ void BKE_icons_free()
gIcons = NULL;
}
+struct PreviewImage* BKE_previewimg_create()
+{
+ PreviewImage* prv_img = NULL;
+ int i;
+
+ prv_img = MEM_callocN(sizeof(PreviewImage), "img_prv");
+
+ for (i=0; i<PREVIEW_MIPMAPS; ++i) {
+ prv_img->changed[i] = 1;
+ }
+ return prv_img;
+}
+
+void BKE_previewimg_free(PreviewImage **prv)
+{
+ if(prv && (*prv)) {
+ int i;
+
+ for (i=0; i<PREVIEW_MIPMAPS;++i) {
+ if ((*prv)->rect[i]) {
+ MEM_freeN((*prv)->rect[i]);
+ (*prv)->rect[i] = NULL;
+ }
+ }
+ MEM_freeN((*prv));
+ *prv = NULL;
+ }
+}
+
+struct PreviewImage* BKE_previewimg_copy(PreviewImage *prv)
+{
+ PreviewImage* prv_img = NULL;
+ int i;
+
+ if (prv) {
+ prv_img = MEM_dupallocN(prv);
+ for (i=0; i < PREVIEW_MIPMAPS; ++i) {
+ if (prv->rect[i]) {
+ prv_img->rect[i] = MEM_dupallocN(prv->rect[i]);
+ } else {
+ prv_img->rect[i] = NULL;
+ }
+ }
+ }
+ return prv_img;
+}
+
+void BKE_previewimg_free_id(ID *id)
+{
+ if (GS(id->name) == ID_MA) {
+ Material *mat = (Material*)id;
+ BKE_previewimg_free(&mat->preview);
+ } else if (GS(id->name) == ID_TE) {
+ Tex *tex = (Tex*)id;
+ BKE_previewimg_free(&tex->preview);
+ } else if (GS(id->name) == ID_WO) {
+ World *wo = (World*)id;
+ BKE_previewimg_free(&wo->preview);
+ } else if (GS(id->name) == ID_LA) {
+ Lamp *la = (Lamp*)id;
+ BKE_previewimg_free(&la->preview);
+ } else if (GS(id->name) == ID_IM) {
+ Image *img = (Image*)id;
+ BKE_previewimg_free(&img->preview);
+ }
+}
+
+PreviewImage* BKE_previewimg_get(ID *id)
+{
+ PreviewImage* prv_img = NULL;
+
+ if (GS(id->name) == ID_MA) {
+ Material *mat = (Material*)id;
+ if (!mat->preview) mat->preview = BKE_previewimg_create();
+ prv_img = mat->preview;
+ } else if (GS(id->name) == ID_TE) {
+ Tex *tex = (Tex*)id;
+ if (!tex->preview) tex->preview = BKE_previewimg_create();
+ prv_img = tex->preview;
+ } else if (GS(id->name) == ID_WO) {
+ World *wo = (World*)id;
+ if (!wo->preview) wo->preview = BKE_previewimg_create();
+ prv_img = wo->preview;
+ } else if (GS(id->name) == ID_LA) {
+ Lamp *la = (Lamp*)id;
+ if (!la->preview) la->preview = BKE_previewimg_create();
+ prv_img = la->preview;
+ } else if (GS(id->name) == ID_IM) {
+ Image *img = (Image*)id;
+ if (!img->preview) img->preview = BKE_previewimg_create();
+ prv_img = img->preview;
+ }
+
+ return prv_img;
+}
void BKE_icon_changed(int id)
{
@@ -122,7 +220,15 @@ void BKE_icon_changed(int id)
if (icon)
{
- icon->changed = 1;
+ PreviewImage *prv = BKE_previewimg_get((ID*)icon->obj);
+
+ /* all previews changed */
+ if (prv) {
+ int i;
+ for (i=0; i<PREVIEW_MIPMAPS; ++i) {
+ prv->changed[i] = 1;
+ }
+ }
}
}
@@ -151,7 +257,6 @@ int BKE_icon_getid(struct ID* id)
/* next two lines make sure image gets created */
new_icon->drawinfo = 0;
new_icon->drawinfo_free = 0;
- new_icon->changed = 1;
BLI_ghash_insert(gIcons, (void *)id->icon_id, new_icon);
diff --git a/source/blender/blenkernel/intern/image.c b/source/blender/blenkernel/intern/image.c
index 2c91c6cb0be..3a64c3504cb 100644
--- a/source/blender/blenkernel/intern/image.c
+++ b/source/blender/blenkernel/intern/image.c
@@ -206,13 +206,6 @@ static void image_free_buffers(Image *ima)
if(ima->anim) IMB_free_anim(ima->anim);
ima->anim= NULL;
- if (ima->preview) {
- if (ima->preview->rect)
- MEM_freeN(ima->preview->rect);
- MEM_freeN(ima->preview);
- ima->preview = NULL;
- }
-
if(ima->rr) {
RE_FreeRenderResult(ima->rr);
ima->rr= NULL;
@@ -234,6 +227,10 @@ void free_image(Image *ima)
}
BKE_icon_delete(&ima->id);
ima->id.icon_id = 0;
+ if (ima->preview) {
+ BKE_previewimg_free(&ima->preview);
+ }
+
}
/* only image block itself */
diff --git a/source/blender/blenkernel/intern/material.c b/source/blender/blenkernel/intern/material.c
index 56b8307020a..f5f726b1745 100644
--- a/source/blender/blenkernel/intern/material.c
+++ b/source/blender/blenkernel/intern/material.c
@@ -90,6 +90,7 @@ void free_material(Material *ma)
if(ma->ramp_col) MEM_freeN(ma->ramp_col);
if(ma->ramp_spec) MEM_freeN(ma->ramp_spec);
+ BKE_previewimg_free(&ma->preview);
BKE_icon_delete((struct ID*)ma);
ma->id.icon_id = 0;
@@ -159,6 +160,8 @@ void init_material(Material *ma)
ma->sss_back= 1.0f;
ma->mode= MA_TRACEBLE|MA_SHADBUF|MA_SHADOW|MA_RADIO|MA_RAYBIAS|MA_TANGENT_STR;
+
+ ma->preview = NULL;
}
Material *add_material(char *name)
@@ -196,6 +199,8 @@ Material *copy_material(Material *ma)
if(ma->ramp_col) man->ramp_col= MEM_dupallocN(ma->ramp_col);
if(ma->ramp_spec) man->ramp_spec= MEM_dupallocN(ma->ramp_spec);
+ if (ma->preview) man->preview = BKE_previewimg_copy(ma->preview);
+
if(ma->nodetree) {
man->nodetree= ntreeCopyTree(ma->nodetree, 0); /* 0 == full new tree */
}
diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c
index 3f26501db6f..349ccda8126 100644
--- a/source/blender/blenkernel/intern/object.c
+++ b/source/blender/blenkernel/intern/object.c
@@ -598,7 +598,7 @@ void *add_lamp(char *name)
la->area_size=la->area_sizey=la->area_sizez= 1.0;
la->buffers= 1;
la->buftype= LA_SHADBUF_HALFWAY;
-
+ la->preview=NULL;
return la;
}
@@ -619,6 +619,8 @@ Lamp *copy_lamp(Lamp *la)
id_us_plus((ID *)lan->ipo);
+ if (la->preview) lan->preview = BKE_previewimg_copy(la->preview);
+
BPY_copy_scriptlink(&la->scriptlink);
return lan;
@@ -696,7 +698,8 @@ void free_lamp(Lamp *la)
if(mtex) MEM_freeN(mtex);
}
la->ipo= 0;
-
+
+ BKE_previewimg_free(&la->preview);
BKE_icon_delete(&la->id);
la->id.icon_id = 0;
}
diff --git a/source/blender/blenkernel/intern/texture.c b/source/blender/blenkernel/intern/texture.c
index bda933802ee..d41ceb5a4b7 100644
--- a/source/blender/blenkernel/intern/texture.c
+++ b/source/blender/blenkernel/intern/texture.c
@@ -390,6 +390,7 @@ void free_texture(Tex *tex)
free_plugin_tex(tex->plugin);
if(tex->coba) MEM_freeN(tex->coba);
if(tex->env) BKE_free_envmap(tex->env);
+ BKE_previewimg_free(&tex->preview);
BKE_icon_delete((struct ID*)tex);
tex->id.icon_id = 0;
}
@@ -462,6 +463,8 @@ void default_tex(Tex *tex)
tex->iuser.fie_ima= 2;
tex->iuser.ok= 1;
tex->iuser.frames= 100;
+
+ tex->preview = NULL;
}
/* ------------------------------------------------------------------------- */
@@ -541,6 +544,8 @@ Tex *copy_texture(Tex *tex)
if(texn->coba) texn->coba= MEM_dupallocN(texn->coba);
if(texn->env) texn->env= BKE_copy_envmap(texn->env);
+ if(tex->preview) texn->preview = BKE_previewimg_copy(tex->preview);
+
return texn;
}
diff --git a/source/blender/blenkernel/intern/world.c b/source/blender/blenkernel/intern/world.c
index 612c095aac7..ce41720cb9d 100644
--- a/source/blender/blenkernel/intern/world.c
+++ b/source/blender/blenkernel/intern/world.c
@@ -75,6 +75,8 @@ void free_world(World *wrld)
if(mtex && mtex->tex) mtex->tex->id.us--;
if(mtex) MEM_freeN(mtex);
}
+ BKE_previewimg_free(&wrld->preview);
+
wrld->ipo= 0;
BKE_icon_delete((struct ID*)wrld);
wrld->id.icon_id = 0;
@@ -102,7 +104,8 @@ World *add_world(char *name)
wrld->aobias= 0.05;
wrld->physicsEngine= WOPHY_BULLET;//WOPHY_SUMO; Bullet by default
-
+ wrld->preview = NULL;
+
return wrld;
}
@@ -121,6 +124,8 @@ World *copy_world(World *wrld)
}
}
+ if (wrld->preview) wrldn->preview = BKE_previewimg_copy(wrld->preview);
+
BPY_copy_scriptlink(&wrld->scriptlink);
id_us_plus((ID *)wrldn->ipo);
diff --git a/source/blender/blenlib/BLI_blenlib.h b/source/blender/blenlib/BLI_blenlib.h
index 6e51d171461..aaa50206ddb 100644
--- a/source/blender/blenlib/BLI_blenlib.h
+++ b/source/blender/blenlib/BLI_blenlib.h
@@ -217,6 +217,11 @@ int BLI_streq(char *a, char *b);
*/
int BLI_strcaseeq(char *a, char *b);
+/* in util.c */
+#ifdef WITH_ICONV
+void BLI_string_to_utf8(char *original, char *utf_8, char *code);
+#endif
+
/**
* Read a file as ASCII lines. An empty list is
* returned if the file cannot be opened or read.
diff --git a/source/blender/blenlib/BLI_storage_types.h b/source/blender/blenlib/BLI_storage_types.h
index 825a8bc9cbd..ebce33852a1 100644
--- a/source/blender/blenlib/BLI_storage_types.h
+++ b/source/blender/blenlib/BLI_storage_types.h
@@ -52,6 +52,8 @@ struct header{
typedef unsigned int mode_t;
#endif
+struct ImBuf;
+
struct direntry{
char *string;
mode_t type;
@@ -68,6 +70,7 @@ struct direntry{
char extra[16];
void *poin;
int nr;
+ struct ImBuf *image;
};
struct dirlink
diff --git a/source/blender/blenlib/intern/util.c b/source/blender/blenlib/intern/util.c
index cfce8e3dafa..2a47dcc300b 100644
--- a/source/blender/blenlib/intern/util.c
+++ b/source/blender/blenlib/intern/util.c
@@ -1491,6 +1491,38 @@ int BLI_strncasecmp(const char *s1, const char *s2, int n) {
return 0;
}
+
+#ifdef WITH_ICONV
+#include "iconv.h"
+#include "localcharset.h"
+
+void BLI_string_to_utf8(char *original, char *utf_8, char *code)
+{
+ size_t inbytesleft=strlen(original);
+ size_t outbytesleft=512;
+ size_t rv=0;
+ iconv_t cd;
+
+ if (NULL == code) {
+ code = locale_charset();
+ }
+ cd=iconv_open("UTF-8", code);
+
+ if (cd == (iconv_t)(-1)) {
+ printf("iconv_open Error");
+ *utf_8='\0';
+ return ;
+ }
+ rv=iconv(cd, &original, &inbytesleft, &utf_8, &outbytesleft);
+ if (rv == (size_t) -1) {
+ printf("iconv Error\n");
+ return ;
+ }
+ *utf_8 = '\0';
+ iconv_close(cd);
+}
+#endif // WITH_ICONV
+
void BLI_timestr(double time, char *str)
{
/* format 00:00:00.00 (hr:min:sec) string has to be 12 long */
diff --git a/source/blender/blenloader/BLO_readfile.h b/source/blender/blenloader/BLO_readfile.h
index 7f621410a4f..09edfe90d02 100644
--- a/source/blender/blenloader/BLO_readfile.h
+++ b/source/blender/blenloader/BLO_readfile.h
@@ -38,12 +38,15 @@ extern "C" {
#endif
struct SpaceFile;
+struct SpaceImaSel;
+struct FileList;
struct LinkNode;
struct Main;
struct UserDef;
struct bScreen;
struct Scene;
struct MemFile;
+struct direntry;
typedef struct BlendHandle BlendHandle;
@@ -192,6 +195,21 @@ BLO_blendhandle_get_datablock_names(
int ofblocktype);
/**
+ * Gets the previews of all the datablocks in a file
+ * of a certain type (ie. All the scene names in
+ * a file).
+ *
+ * @param bh The blendhandle to access.
+ * @param ofblocktype The type of names to get.
+ * @return A BLI_linklist of PreviewImage. The PreviewImage links
+ * should be freed with malloc.
+ */
+ struct LinkNode*
+BLO_blendhandle_get_previews(
+ BlendHandle *bh,
+ int ofblocktype);
+
+/**
* Gets the names of all the datablock groups in a
* file. (ie. file contains Scene, Mesh, and Lamp
* datablocks).
@@ -219,6 +237,7 @@ BLO_blendhandle_close(
char *BLO_gethome(void);
int BLO_has_bfile_extension(char *str);
void BLO_library_append(struct SpaceFile *sfile, char *dir, int idcode);
+void BLO_library_append_(BlendHandle **libfiledata, struct direntry* filelist, int totfile, char *dir, char* file, short flag, int idcode);
void BLO_script_library_append(BlendHandle *bh, char *dir, char *name, int idcode, short flag, struct Scene *scene);
BlendFileData* blo_read_blendafterruntime(int file, int actualsize, BlendReadError *error_r);
diff --git a/source/blender/blenloader/intern/readblenentry.c b/source/blender/blenloader/intern/readblenentry.c
index 5f67c060c04..dfa06ebdeb8 100644
--- a/source/blender/blenloader/intern/readblenentry.c
+++ b/source/blender/blenloader/intern/readblenentry.c
@@ -50,6 +50,7 @@
#include "DNA_space_types.h"
#include "DNA_userdef_types.h"
#include "DNA_ID.h"
+#include "DNA_material_types.h"
#include "BKE_utildefines.h" // for ENDB
@@ -61,6 +62,7 @@
#include "BLO_undofile.h"
#include "readfile.h"
+#include "genfile.h"
#include "BLO_readblenfile.h"
@@ -218,6 +220,70 @@ LinkNode *BLO_blendhandle_get_datablock_names(BlendHandle *bh, int ofblocktype)
return names;
}
+LinkNode *BLO_blendhandle_get_previews(BlendHandle *bh, int ofblocktype)
+{
+ FileData *fd= (FileData*) bh;
+ LinkNode *previews= NULL;
+ BHead *bhead;
+ int looking=0;
+ int npreviews = 0;
+ PreviewImage* prv = NULL;
+ PreviewImage* new_prv = NULL;
+
+ for (bhead= blo_firstbhead(fd); bhead; bhead= blo_nextbhead(fd, bhead)) {
+ if (bhead->code==ofblocktype) {
+ ID *id= (ID*) (bhead+1);
+ if (GS(id->name) == ID_MA) {
+ new_prv = MEM_callocN(sizeof(PreviewImage), "newpreview");
+ BLI_linklist_prepend(&previews, new_prv);
+ looking = 1;
+ }
+ } else if (bhead->code==DATA) {
+ if (looking) {
+ if (bhead->SDNAnr == dna_findstruct_nr(fd->filesdna, "PreviewImage") ) {
+ prv = (PreviewImage*) (bhead+1);
+ npreviews = 0;
+ memcpy(new_prv, prv, sizeof(PreviewImage));
+ if (prv->rect[0]) {
+ unsigned int *rect = NULL;
+ int rectlen = 0;
+ new_prv->rect[0] = MEM_callocN(new_prv->w[0]*new_prv->h[0]*sizeof(unsigned int), "prvrect");
+ bhead= blo_nextbhead(fd, bhead);
+ rect = (unsigned int*)(bhead+1);
+ rectlen = new_prv->w[0]*new_prv->h[0]*sizeof(unsigned int);
+ memcpy(new_prv->rect[0], rect, bhead->len);
+ } else {
+ new_prv->rect[0] = NULL;
+ }
+
+ if (prv->rect[1]) {
+ unsigned int *rect = NULL;
+ int rectlen = 0;
+ new_prv->rect[1] = MEM_callocN(new_prv->w[1]*new_prv->h[1]*sizeof(unsigned int), "prvrect");
+ bhead= blo_nextbhead(fd, bhead);
+ rect = (unsigned int*)(bhead+1);
+ rectlen = new_prv->w[1]*new_prv->h[1]*sizeof(unsigned int);
+ memcpy(new_prv->rect[1], rect, bhead->len);
+ } else {
+ new_prv->rect[1] = NULL;
+ }
+ }
+ }
+ } else if (bhead->code==ENDB) {
+ break;
+ } else if (bhead->code==DATA) {
+ /* DATA blocks between IDBlock and Preview */
+ } else {
+ looking = 0;
+ new_prv = NULL;
+ prv = NULL;
+ }
+
+ }
+
+ return previews;
+}
+
LinkNode *BLO_blendhandle_get_linkable_groups(BlendHandle *bh)
{
FileData *fd= (FileData*) bh;
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index fa21161f8eb..1f1dd84f49c 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -137,6 +137,7 @@
#include "BKE_idprop.h"
#include "BIF_butspace.h" // badlevel, for do_versions, patching event codes
+#include "BIF_filelist.h" // badlevel too, where to move this? - elubie
#include "BIF_previewrender.h" // bedlelvel, for struct RenderInfo
#include "BLO_readfile.h"
#include "BLO_undofile.h"
@@ -1541,7 +1542,12 @@ static PreviewImage *direct_link_preview_image(FileData *fd, PreviewImage *old_p
PreviewImage *prv= newdataadr(fd, old_prv);
if (prv) {
- prv->rect = newdataadr(fd, prv->rect);
+ int i;
+ for (i=0; i < PREVIEW_MIPMAPS; ++i) {
+ if (prv->rect[i]) {
+ prv->rect[i] = newdataadr(fd, prv->rect[i]);
+ }
+ }
}
return prv;
@@ -1911,6 +1917,7 @@ static void direct_link_lamp(FileData *fd, Lamp *la)
for(a=0; a<MAX_MTEX; a++) {
la->mtex[a]= newdataadr(fd, la->mtex[a]);
}
+ la->preview = direct_link_preview_image(fd, la->preview);
}
/* ************ READ keys ***************** */
@@ -2058,6 +2065,7 @@ static void direct_link_world(FileData *fd, World *wrld)
for(a=0; a<MAX_MTEX; a++) {
wrld->mtex[a]= newdataadr(fd, wrld->mtex[a]);
}
+ wrld->preview = direct_link_preview_image(fd, wrld->preview);
}
@@ -2367,6 +2375,8 @@ static void direct_link_texture(FileData *fd, Tex *tex)
memset(tex->env->cube, 0, 6*sizeof(void *));
tex->env->ok= 0;
}
+ tex->preview = direct_link_preview_image(fd, tex->preview);
+
tex->iuser.ok= 1;
}
@@ -2424,6 +2434,8 @@ static void direct_link_material(FileData *fd, Material *ma)
ma->nodetree= newdataadr(fd, ma->nodetree);
if(ma->nodetree)
direct_link_nodetree(fd, ma->nodetree);
+
+ ma->preview = direct_link_preview_image(fd, ma->preview);
}
/* ************ READ MESH ***************** */
@@ -3448,7 +3460,13 @@ static void lib_link_screen(FileData *fd, Main *main)
sfile->pupmenu= NULL;
}
else if(sl->spacetype==SPACE_IMASEL) {
- check_imasel_copy((SpaceImaSel *)sl);
+ SpaceImaSel *simasel= (SpaceImaSel *)sl;
+
+ simasel->files = NULL;
+ simasel->returnfunc= NULL;
+ simasel->menup= NULL;
+ simasel->pupmenu= NULL;
+ simasel->img= NULL;
}
else if(sl->spacetype==SPACE_ACTION) {
SpaceAction *saction= (SpaceAction *)sl;
@@ -3618,7 +3636,10 @@ void lib_link_screen_restore(Main *newmain, Scene *curscene)
sfile->libfiledata= 0;
}
else if(sl->spacetype==SPACE_IMASEL) {
- ;
+ SpaceImaSel *simasel= (SpaceImaSel *)sl;
+ if (simasel->files) {
+ BIF_filelist_freelib(simasel->files);
+ }
}
else if(sl->spacetype==SPACE_ACTION) {
SpaceAction *saction= (SpaceAction *)sl;
@@ -6481,6 +6502,62 @@ static void do_versions(FileData *fd, Library *lib, Main *main)
Mesh *me;
for(me=main->mesh.first; me; me=me->id.next)
customdata_version_243(me);
+ }
+
+ }
+
+
+ if (main->versionfile < 244) {
+ bScreen *sc;
+ Image* ima;
+
+ /* repair preview from 242 */
+ for(ima= main->image.first; ima; ima= ima->id.next) {
+ ima->preview = NULL;
+ }
+
+ /* repair imasel space - completely reworked */
+ for(sc= main->screen.first; sc; sc= sc->id.next) {
+ ScrArea *sa;
+ sa= sc->areabase.first;
+ while(sa) {
+ SpaceLink *sl;
+
+ for (sl= sa->spacedata.first; sl; sl= sl->next) {
+ if(sl->spacetype==SPACE_IMASEL) {
+ SpaceImaSel *simasel= (SpaceImaSel*) sl;
+ simasel->blockscale= 0.7;
+ /* view 2D */
+ simasel->v2d.tot.xmin= -10.0;
+ simasel->v2d.tot.ymin= -10.0;
+ simasel->v2d.tot.xmax= (float)sa->winx + 10.0f;
+ simasel->v2d.tot.ymax= (float)sa->winy + 10.0f;
+ simasel->v2d.cur.xmin= 0.0;
+ simasel->v2d.cur.ymin= 0.0;
+ simasel->v2d.cur.xmax= (float)sa->winx;
+ simasel->v2d.cur.ymax= (float)sa->winy;
+ simasel->v2d.min[0]= 1.0;
+ simasel->v2d.min[1]= 1.0;
+ simasel->v2d.max[0]= 32000.0f;
+ simasel->v2d.max[1]= 32000.0f;
+ simasel->v2d.minzoom= 0.5f;
+ simasel->v2d.maxzoom= 1.21f;
+ simasel->v2d.scroll= 0;
+ simasel->v2d.keepaspect= 1;
+ simasel->v2d.keepzoom= 1;
+ simasel->v2d.keeptot= 0;
+ simasel->prv_h = 96;
+ simasel->prv_w = 96;
+ simasel->flag = 7; /* ??? elubie */
+ strcpy (simasel->dir, U.textudir); /* TON */
+ strcpy (simasel->file, "");
+
+ simasel->returnfunc = 0;
+ simasel->title[0] = 0;
+ }
+ }
+ sa = sa->next;
+ }
}
}
if(main->versionfile <= 244) {
@@ -7550,8 +7627,8 @@ static void append_id_part(FileData *fd, Main *mainvar, ID *id, ID **id_r)
/* common routine to append/link something from a library */
-static Library* library_append( Scene *scene, SpaceFile *sfile, char *dir, int idcode,
- int totsel, FileData *fd)
+static Library* library_append( Scene *scene, char* file, char *dir, int idcode,
+ int totsel, FileData *fd, struct direntry* filelist, int totfile, short flag)
{
Main *mainl;
Library *curlib;
@@ -7567,13 +7644,13 @@ static Library* library_append( Scene *scene, SpaceFile *sfile, char *dir, int i
curlib= mainl->curlib;
if(totsel==0) {
- append_named_part(fd, mainl, scene, sfile->file, idcode, sfile->flag);
+ append_named_part(fd, mainl, scene, file, idcode, flag);
}
else {
int a;
- for(a=0; a<sfile->totfile; a++) {
- if(sfile->filelist[a].flags & ACTIVE) {
- append_named_part(fd, mainl, scene, sfile->filelist[a].relname, idcode, sfile->flag);
+ for(a=0; a<totfile; a++) {
+ if(filelist[a].flags & ACTIVE) {
+ append_named_part(fd, mainl, scene, filelist[a].relname, idcode, flag);
}
}
}
@@ -7584,7 +7661,7 @@ static Library* library_append( Scene *scene, SpaceFile *sfile, char *dir, int i
/* do this when expand found other libs */
read_libraries(fd, &fd->mainlist);
- if(sfile->flag & FILE_STRINGCODE) {
+ if(flag & FILE_STRINGCODE) {
/* use the full path, this could have been read by other library even */
BLI_strncpy(mainl->curlib->name, mainl->curlib->filename, sizeof(mainl->curlib->name));
@@ -7601,7 +7678,7 @@ static Library* library_append( Scene *scene, SpaceFile *sfile, char *dir, int i
/* give a base to loose objects. If group append, do it for objects too */
if(idcode==ID_GR)
- give_base_to_objects(scene, &(G.main->object), (sfile->flag & FILE_LINK)?NULL:curlib);
+ give_base_to_objects(scene, &(G.main->object), (flag & FILE_LINK)?NULL:curlib);
else
give_base_to_objects(scene, &(G.main->object), NULL);
@@ -7612,8 +7689,7 @@ static Library* library_append( Scene *scene, SpaceFile *sfile, char *dir, int i
/* patch to prevent switch_endian happens twice */
if(fd->flags & FD_FLAGS_SWITCH_ENDIAN) {
blo_freefiledata( fd );
- sfile->libfiledata= 0;
- }
+ }
return curlib;
}
@@ -7626,16 +7702,8 @@ static Library* library_append( Scene *scene, SpaceFile *sfile, char *dir, int i
void BLO_script_library_append(BlendHandle *bh, char *dir, char *name,
int idcode, short flag, Scene *scene )
{
- SpaceFile sfile;
-
- /* build a minimal "fake" SpaceFile object */
- sfile.flag = flag;
- sfile.totfile = 0;
- strcpy(sfile.file, name);
-
/* try to append the requested object */
-
- library_append( scene, &sfile, dir, idcode, 0, (FileData *)bh );
+ library_append( scene, name, dir, idcode, 0, (FileData *)bh, NULL, 0, flag );
/* do we need to do this? */
DAG_scene_sort(G.scene);
@@ -7645,26 +7713,31 @@ void BLO_script_library_append(BlendHandle *bh, char *dir, char *name,
/* dir is a full path */
void BLO_library_append(SpaceFile *sfile, char *dir, int idcode)
{
- FileData *fd= (FileData*) sfile->libfiledata;
+ BLO_library_append_(&sfile->libfiledata, sfile->filelist, sfile->totfile, dir, sfile->file, sfile->flag, idcode);
+}
+
+void BLO_library_append_(BlendHandle** libfiledata, struct direntry* filelist, int totfile, char *dir, char* file, short flag, int idcode)
+{
+ FileData *fd= (FileData*) (*libfiledata);
Library *curlib;
Base *centerbase;
Object *ob;
int a, totsel=0;
/* are there files selected? */
- for(a=0; a<sfile->totfile; a++) {
- if(sfile->filelist[a].flags & ACTIVE) {
+ for(a=0; a<totfile; a++) {
+ if(filelist[a].flags & ACTIVE) {
totsel++;
}
}
if(totsel==0) {
/* is the indicated file in the filelist? */
- if(sfile->file[0]) {
- for(a=0; a<sfile->totfile; a++) {
- if( strcmp(sfile->filelist[a].relname, sfile->file)==0) break;
+ if(file[0]) {
+ for(a=0; a<totfile; a++) {
+ if( strcmp(filelist[a].relname, file)==0) break;
}
- if(a==sfile->totfile) {
+ if(a==totfile) {
error("Wrong indicated name");
return;
}
@@ -7676,13 +7749,18 @@ void BLO_library_append(SpaceFile *sfile, char *dir, int idcode)
}
/* now we have or selected, or an indicated file */
- if(sfile->flag & FILE_AUTOSELECT) scene_deselect_all(G.scene);
+ if(flag & FILE_AUTOSELECT) scene_deselect_all(G.scene);
+
+ curlib = library_append( G.scene, file, dir, idcode, totsel, fd, filelist, totfile,flag );
- curlib = library_append( G.scene, sfile, dir, idcode, totsel, fd );
+ /* patch to prevent switch_endian happens twice */
+ if(fd->flags & FD_FLAGS_SWITCH_ENDIAN) {
+ (*libfiledata)= 0;
+ }
/* when not linking (appending)... */
- if((sfile->flag & FILE_LINK)==0) {
- if(sfile->flag & FILE_ATCURSOR) {
+ if((flag & FILE_LINK)==0) {
+ if(flag & FILE_ATCURSOR) {
float *curs, centerloc[3], vec[3], min[3], max[3];
int count= 0;
diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c
index ee914954b90..90873efb5b9 100644
--- a/source/blender/blenloader/intern/writefile.c
+++ b/source/blender/blenloader/intern/writefile.c
@@ -1222,6 +1222,31 @@ static void write_lattices(WriteData *wd, ListBase *idbase)
}
}
+static void write_previews(WriteData *wd, PreviewImage *prv)
+{
+ if (prv) {
+ short w = prv->w[1];
+ short h = prv->h[1];
+ unsigned int *rect = prv->rect[1];
+ /* don't write out large previews if not requested */
+ if (!(U.flag & USER_SAVE_PREVIEWS) ) {
+ prv->w[1] = 0;
+ prv->h[1] = 0;
+ prv->rect[1] = NULL;
+ }
+ writestruct(wd, DATA, "PreviewImage", 1, prv);
+ if (prv->rect[0]) writedata(wd, DATA, prv->w[0]*prv->h[0]*sizeof(unsigned int), prv->rect[0]);
+ if (prv->rect[1]) writedata(wd, DATA, prv->w[1]*prv->h[1]*sizeof(unsigned int), prv->rect[1]);
+
+ /* restore preview, we still want to keep it in memory even if not saved to file */
+ if (!(U.flag & USER_SAVE_PREVIEWS) ) {
+ prv->w[1] = w;
+ prv->h[1] = h;
+ prv->rect[1] = rect;
+ }
+ }
+}
+
static void write_images(WriteData *wd, ListBase *idbase)
{
Image *ima;
@@ -1241,12 +1266,9 @@ static void write_images(WriteData *wd, ListBase *idbase)
writedata(wd, DATA, pf->size, pf->data);
}
- if (ima->preview) {
- PreviewImage *prv = ima->preview;
- writestruct(wd, DATA, "PreviewImage", 1, prv);
- writedata(wd, DATA, prv->w*prv->h*sizeof(unsigned int), prv->rect);
+ write_previews(wd, ima->preview);
+
}
- }
ima= ima->id.next;
}
/* flush helps the compression for undo-save */
@@ -1268,6 +1290,8 @@ static void write_textures(WriteData *wd, ListBase *idbase)
if(tex->plugin) writestruct(wd, DATA, "PluginTex", 1, tex->plugin);
if(tex->coba) writestruct(wd, DATA, "ColorBand", 1, tex->coba);
if(tex->env) writestruct(wd, DATA, "EnvMap", 1, tex->env);
+
+ write_previews(wd, tex->preview);
}
tex= tex->id.next;
}
@@ -1307,6 +1331,8 @@ static void write_materials(WriteData *wd, ListBase *idbase)
writestruct(wd, DATA, "bNodeTree", 1, ma->nodetree);
write_nodetree(wd, ma->nodetree);
}
+
+ write_previews(wd, ma->preview);
}
ma= ma->id.next;
}
@@ -1329,6 +1355,9 @@ static void write_worlds(WriteData *wd, ListBase *idbase)
}
write_scriptlink(wd, &wrld->scriptlink);
+
+ write_previews(wd, wrld->preview);
+
}
wrld= wrld->id.next;
}
@@ -1352,6 +1381,9 @@ static void write_lamps(WriteData *wd, ListBase *idbase)
}
write_scriptlink(wd, &la->scriptlink);
+
+ write_previews(wd, la->preview);
+
}
la= la->id.next;
}
diff --git a/source/blender/imbuf/IMB_imbuf.h b/source/blender/imbuf/IMB_imbuf.h
index 840d39ea0bd..3e8aaea4f3c 100644
--- a/source/blender/imbuf/IMB_imbuf.h
+++ b/source/blender/imbuf/IMB_imbuf.h
@@ -280,6 +280,13 @@ struct ImBuf * IMB_anim_absolute(struct anim * anim, int position);
/**
*
* @attention Defined in anim.c
+ * fetches a define previewframe, usually half way into the movie
+ */
+struct ImBuf * IMB_anim_previewframe(struct anim * anim);
+
+/**
+ *
+ * @attention Defined in anim.c
*/
void IMB_free_anim_ibuf(struct anim * anim);
diff --git a/source/blender/imbuf/IMB_imbuf_types.h b/source/blender/imbuf/IMB_imbuf_types.h
index d43b78df0b6..91ffa188fcc 100644
--- a/source/blender/imbuf/IMB_imbuf_types.h
+++ b/source/blender/imbuf/IMB_imbuf_types.h
@@ -56,6 +56,8 @@
struct _AviMovie;
struct Mdec;
+struct ImgInfo;
+
#define IB_MIPMAP_LEVELS 10
/**
@@ -103,6 +105,7 @@ typedef struct ImBuf {
float dither; /**< random dither value, for conversion from float -> byte rect */
struct MEM_CacheLimiterHandle_s * c_handle; /**< handle for cache limiter */
+ struct ImgInfo * img_info;
int refcounter; /**< Refcounter for multiple users */
int index; /**< reference index for ImBuf lists */
@@ -148,6 +151,7 @@ typedef enum {
#define IB_rectfloat (1 << 15)
#define IB_zbuffloat (1 << 16)
#define IB_multilayer (1 << 17)
+#define IB_imginfo (1 << 18)
/*
* The bit flag is stored in the ImBuf.ftype variable.
diff --git a/source/blender/imbuf/IMB_thumbs.h b/source/blender/imbuf/IMB_thumbs.h
new file mode 100644
index 00000000000..22565dac688
--- /dev/null
+++ b/source/blender/imbuf/IMB_thumbs.h
@@ -0,0 +1,73 @@
+/**
+ * $Id: $
+ *
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2007 Blender Foundation
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): Andrea Weikert.
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+#ifndef _IMB_THUMBS_H
+#define _IMB_THUMBS_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct ImBuf;
+
+/** Thumbnail creation and retrieval according to the 'Thumbnail Management Standard'
+ * supported by Gimp, Gnome (Nautilus), KDE etc.
+ * Reference: http://jens.triq.net/thumbnail-spec/index.html
+ */
+
+
+typedef enum ThumbSize {
+ THB_NORMAL,
+ THB_LARGE,
+ THB_FAIL
+} ThumbSize;
+
+typedef enum ThumbSource {
+ THB_SOURCE_IMAGE,
+ THB_SOURCE_MOVIE
+} ThumbSource;
+
+// IB_imginfo
+
+/* create thumbnail for file and returns new imbuf for thumbnail */
+ImBuf* IMB_thumb_create(const char* dir, const char* file, ThumbSize size, ThumbSource source);
+
+/* read thumbnail for file and returns new imbuf for thumbnail */
+ImBuf* IMB_thumb_read(const char* dir, const char* file, ThumbSize size);
+
+/* delete all thumbs for the file */
+void IMB_thumb_delete(const char* dir, const char* file, ThumbSize size);
+
+/* return the state of the thumb, needed to determine how to manage the thumb */
+ImBuf* IMB_thumb_manage(const char* dir, const char* file, ThumbSize size, ThumbSource source);
+
+
+
+
+#endif /* _IMB_THUMBS_H */
diff --git a/source/blender/imbuf/intern/IMB_imginfo.h b/source/blender/imbuf/intern/IMB_imginfo.h
new file mode 100644
index 00000000000..91073ec9575
--- /dev/null
+++ b/source/blender/imbuf/intern/IMB_imginfo.h
@@ -0,0 +1,78 @@
+/**
+ * $Id: $
+ *
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2005 Blender Foundation
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): Austin Benesh. Ton Roosendaal.
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+#ifndef _IMB_IMGINFO_H
+#define _IMB_IMGINFO_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct ImBuf;
+
+typedef struct ImgInfo {
+ struct ImgInfo *next, *prev;
+ char* key;
+ char* value;
+ int len;
+} ImgInfo;
+
+/** The imginfo is a list of key/value pairs (both char*) that can me
+ saved in the header of several image formats.
+ Apart from some common keys like
+ 'Software' and 'Description' (png standard) we'll use keys within the
+ Blender namespace, so should be called 'Blender::StampInfo' or 'Blender::FrameNum'
+ etc...
+*/
+
+
+/* free blender ImgInfo struct */
+void IMB_imginfo_free(struct ImBuf* img);
+
+/** read the field from the image info into the field
+ * @param img - the ImBuf that contains the image data
+ * @param key - the key of the field
+ * @param value - the data in the field, first one found with key is returned,
+ memory has to be allocated by user.
+ * @param len - length of value buffer allocated by user.
+ * @return - 1 (true) if ImageInfo present and value for the key found, 0 (false) otherwise
+ */
+int IMB_imginfo_get_field(struct ImBuf* img, const char* key, char* value, int len);
+
+/** set user data in the ImgInfo struct, which has to be allocated with IMB_imginfo_create
+ * before calling this function.
+ * @param img - the ImBuf that contains the image data
+ * @param key - the key of the field
+ * @param value - the data to be written to the field. zero terminated string
+ * @return - 1 (true) if ImageInfo present, 0 (false) otherwise
+ */
+int IMB_imginfo_add_field(struct ImBuf* img, const char* key, const char* field);
+
+
+#endif /* _IMB_IMGINFO_H */
diff --git a/source/blender/imbuf/intern/allocimbuf.c b/source/blender/imbuf/intern/allocimbuf.c
index 003d377389b..a5d404740cf 100644
--- a/source/blender/imbuf/intern/allocimbuf.c
+++ b/source/blender/imbuf/intern/allocimbuf.c
@@ -43,6 +43,7 @@
#include "IMB_divers.h"
#include "IMB_allocimbuf.h"
+#include "IMB_imginfo.h"
#include "MEM_CacheLimiterC-Api.h"
static unsigned int dfltcmap[16] = {
@@ -163,6 +164,7 @@ void IMB_freeImBuf(struct ImBuf * ibuf)
IMB_freecmapImBuf(ibuf);
freeencodedbufferImBuf(ibuf);
IMB_cache_limiter_unmanage(ibuf);
+ IMB_imginfo_free(ibuf);
MEM_freeN(ibuf);
}
}
@@ -476,6 +478,9 @@ struct ImBuf *IMB_dupImBuf(struct ImBuf *ibuf1)
tbuf.mall = ibuf2->mall;
tbuf.c_handle = 0;
+ // for now don't duplicate image info
+ tbuf.img_info = 0;
+
*ibuf2 = tbuf;
if (ibuf1->cmap){
diff --git a/source/blender/imbuf/intern/anim.c b/source/blender/imbuf/intern/anim.c
index a1ef735ffdb..24ea79ee90d 100644
--- a/source/blender/imbuf/intern/anim.c
+++ b/source/blender/imbuf/intern/anim.c
@@ -819,6 +819,18 @@ static struct ImBuf * anim_getnew(struct anim * anim) {
return(ibuf);
}
+struct ImBuf * IMB_anim_previewframe(struct anim * anim) {
+ struct ImBuf * ibuf = 0;
+ int position = 0;
+
+ ibuf = IMB_anim_absolute(anim, 0);
+ if (ibuf) {
+ IMB_freeImBuf(ibuf);
+ position = anim->duration / 2;
+ ibuf = IMB_anim_absolute(anim, position);
+ }
+ return ibuf;
+}
struct ImBuf * IMB_anim_absolute(struct anim * anim, int position) {
struct ImBuf * ibuf = 0;
diff --git a/source/blender/imbuf/intern/imginfo.c b/source/blender/imbuf/intern/imginfo.c
new file mode 100644
index 00000000000..c443b1be885
--- /dev/null
+++ b/source/blender/imbuf/intern/imginfo.c
@@ -0,0 +1,108 @@
+/**
+ * $Id: $
+ *
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2005 Blender Foundation
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): Austin Benesh. Ton Roosendaal.
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "BLI_blenlib.h"
+#include "MEM_guardedalloc.h"
+
+#include "IMB_imbuf_types.h"
+#include "IMB_imbuf.h"
+
+#include "IMB_imginfo.h"
+
+
+
+void IMB_imginfo_free(struct ImBuf* img)
+{
+ ImgInfo *info;
+
+ if (!img)
+ return;
+ if (!img->img_info) {
+ return;
+ }
+ info = img->img_info;
+ while (info) {
+ ImgInfo* next = info->next;
+ MEM_freeN(info->key);
+ MEM_freeN(info->value);
+ MEM_freeN(info);
+ info = next;
+ }
+}
+
+int IMB_imginfo_get_field(struct ImBuf* img, const char* key, char* field, int len)
+{
+ ImgInfo *info;
+ int retval = 0;
+
+ if (!img)
+ return 0;
+ if (!img->img_info) {
+ return 0;
+ }
+ info = img->img_info;
+ while (info) {
+ if (strcmp(key, info->key) == 0) {
+ BLI_strncpy(field, info->value, len);
+ retval = 1;
+ break;
+ }
+ info = info->next;
+ }
+ return retval;
+}
+
+int IMB_imginfo_add_field(struct ImBuf* img, const char* key, const char* field)
+{
+ ImgInfo *info;
+ ImgInfo *last;
+
+ if (!img)
+ return 0;
+
+ if (!img->img_info) {
+ img->img_info = MEM_callocN(sizeof(ImgInfo), "ImgInfo");
+ info = img->img_info;
+ } else {
+ info = img->img_info;
+ last = info;
+ while (info) {
+ last = info;
+ info = info->next;
+ }
+ info = MEM_callocN(sizeof(ImgInfo), "ImgInfo");
+ last->next = info;
+ }
+ info->key = BLI_strdup(key);
+ info->value = BLI_strdup(field);
+ return 1;
+}
diff --git a/source/blender/imbuf/intern/md5.c b/source/blender/imbuf/intern/md5.c
new file mode 100644
index 00000000000..3119dd1fe7d
--- /dev/null
+++ b/source/blender/imbuf/intern/md5.c
@@ -0,0 +1,360 @@
+/* md5.c - Functions to compute MD5 message digest of files or memory blocks
+ according to the definition of MD5 in RFC 1321 from April 1992.
+ Copyright (C) 1995 Software Foundation, Inc.
+
+ 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, 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., 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+/* Written by Ulrich Drepper <drepper@gnu.ai.mit.edu>. */
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+
+#include <sys/types.h>
+
+# include <stdlib.h>
+# include <string.h>
+
+#include "md5.h"
+
+#ifdef WORDS_BIGENDIAN
+# define SWAP(n) \
+ (((n) << 24) | (((n) & 0xff00) << 8) | (((n) >> 8) & 0xff00) | ((n) >> 24))
+#else
+# define SWAP(n) (n)
+#endif
+
+
+/* This array contains the bytes used to pad the buffer to the next
+ 64-byte boundary. (RFC 1321, 3.1: Step 1) */
+static const unsigned char fillbuf[64] = { 0x80, 0 /* , 0, 0, ... */ };
+
+
+/* Initialize structure containing state of computation.
+ (RFC 1321, 3.3: Step 3) */
+void
+md5_init_ctx (ctx)
+ struct md5_ctx *ctx;
+{
+ ctx->A = 0x67452301;
+ ctx->B = 0xefcdab89;
+ ctx->C = 0x98badcfe;
+ ctx->D = 0x10325476;
+}
+
+/* Put result from CTX in first 16 bytes following RESBUF. The result must
+ be in little endian byte order. */
+void *
+md5_read_ctx (ctx, resbuf)
+ const struct md5_ctx *ctx;
+ void *resbuf;
+{
+ ((md5_uint32 *) resbuf)[0] = SWAP (ctx->A);
+ ((md5_uint32 *) resbuf)[1] = SWAP (ctx->B);
+ ((md5_uint32 *) resbuf)[2] = SWAP (ctx->C);
+ ((md5_uint32 *) resbuf)[3] = SWAP (ctx->D);
+
+ return resbuf;
+}
+
+/* Compute MD5 message digest for bytes read from STREAM. The
+ resulting message digest number will be written into the 16 bytes
+ beginning at RESBLOCK. */
+int
+md5_stream (stream, resblock)
+ FILE *stream;
+ void *resblock;
+{
+ /* Important: BLOCKSIZE must be a multiple of 64. */
+#define BLOCKSIZE 4096
+ struct md5_ctx ctx;
+ md5_uint32 len[2];
+ char buffer[BLOCKSIZE + 72];
+ size_t pad, sum;
+
+ /* Initialize the computation context. */
+ md5_init_ctx (&ctx);
+
+ len[0] = 0;
+ len[1] = 0;
+
+ /* Iterate over full file contents. */
+ while (1)
+ {
+ /* We read the file in blocks of BLOCKSIZE bytes. One call of the
+ computation function processes the whole buffer so that with the
+ next round of the loop another block can be read. */
+ size_t n;
+ sum = 0;
+
+ /* Read block. Take care for partial reads. */
+ do
+ {
+ n = fread (buffer, 1, BLOCKSIZE - sum, stream);
+
+ sum += n;
+ }
+ while (sum < BLOCKSIZE && n != 0);
+ if (n == 0 && ferror (stream))
+ return 1;
+
+ /* RFC 1321 specifies the possible length of the file up to 2^64 bits.
+ Here we only compute the number of bytes. Do a double word
+ increment. */
+ len[0] += sum;
+ if (len[0] < sum)
+ ++len[1];
+
+ /* If end of file is reached, end the loop. */
+ if (n == 0)
+ break;
+
+ /* Process buffer with BLOCKSIZE bytes. Note that
+ BLOCKSIZE % 64 == 0
+ */
+ md5_process_block (buffer, BLOCKSIZE, &ctx);
+ }
+
+ /* We can copy 64 byte because the buffer is always big enough. FILLBUF
+ contains the needed bits. */
+ memcpy (&buffer[sum], fillbuf, 64);
+
+ /* Compute amount of padding bytes needed. Alignment is done to
+ (N + PAD) % 64 == 56
+ There is always at least one byte padded. I.e. even the alignment
+ is correctly aligned 64 padding bytes are added. */
+ pad = sum & 63;
+ pad = pad >= 56 ? 64 + 56 - pad : 56 - pad;
+
+ /* Put the 64-bit file length in *bits* at the end of the buffer. */
+ *(md5_uint32 *) &buffer[sum + pad] = SWAP (len[0] << 3);
+ *(md5_uint32 *) &buffer[sum + pad + 4] = SWAP ((len[1] << 3)
+ | (len[0] >> 29));
+
+ /* Process last bytes. */
+ md5_process_block (buffer, sum + pad + 8, &ctx);
+
+ /* Construct result in desired memory. */
+ md5_read_ctx (&ctx, resblock);
+ return 0;
+}
+
+/* Compute MD5 message digest for LEN bytes beginning at BUFFER. The
+ result is always in little endian byte order, so that a byte-wise
+ output yields to the wanted ASCII representation of the message
+ digest. */
+void *
+md5_buffer (buffer, len, resblock)
+ const char *buffer;
+ size_t len;
+ void *resblock;
+{
+ struct md5_ctx ctx;
+ char restbuf[64 + 72];
+ size_t blocks = len & ~63;
+ size_t pad, rest;
+
+ /* Initialize the computation context. */
+ md5_init_ctx (&ctx);
+
+ /* Process whole buffer but last len % 64 bytes. */
+ md5_process_block (buffer, blocks, &ctx);
+
+ /* REST bytes are not processed yet. */
+ rest = len - blocks;
+ /* Copy to own buffer. */
+ memcpy (restbuf, &buffer[blocks], rest);
+ /* Append needed fill bytes at end of buffer. We can copy 64 byte
+ because the buffer is always big enough. */
+ memcpy (&restbuf[rest], fillbuf, 64);
+
+ /* PAD bytes are used for padding to correct alignment. Note that
+ always at least one byte is padded. */
+ pad = rest >= 56 ? 64 + 56 - rest : 56 - rest;
+
+ /* Put length of buffer in *bits* in last eight bytes. */
+ *(md5_uint32 *) &restbuf[rest + pad] = (md5_uint32) SWAP (len << 3);
+ *(md5_uint32 *) &restbuf[rest + pad + 4] = (md5_uint32) SWAP (len >> 29);
+
+ /* Process last bytes. */
+ md5_process_block (restbuf, rest + pad + 8, &ctx);
+
+ /* Put result in desired memory area. */
+ return md5_read_ctx (&ctx, resblock);
+}
+
+
+/* These are the four functions used in the four steps of the MD5 algorithm
+ and defined in the RFC 1321. The first function is a little bit optimized
+ (as found in Colin Plumbs public domain implementation). */
+/* #define FF(b, c, d) ((b & c) | (~b & d)) */
+#define FF(b, c, d) (d ^ (b & (c ^ d)))
+#define FG(b, c, d) FF (d, b, c)
+#define FH(b, c, d) (b ^ c ^ d)
+#define FI(b, c, d) (c ^ (b | ~d))
+
+/* Process LEN bytes of BUFFER, accumulating context into CTX.
+ It is assumed that LEN % 64 == 0. */
+
+void
+md5_process_block (buffer, len, ctx)
+ const void *buffer;
+ size_t len;
+ struct md5_ctx *ctx;
+{
+ md5_uint32 correct_words[16];
+ const md5_uint32 *words = buffer;
+ size_t nwords = len / sizeof (md5_uint32);
+ const md5_uint32 *endp = words + nwords;
+ md5_uint32 A = ctx->A;
+ md5_uint32 B = ctx->B;
+ md5_uint32 C = ctx->C;
+ md5_uint32 D = ctx->D;
+
+ /* Process all bytes in the buffer with 64 bytes in each round of
+ the loop. */
+ while (words < endp)
+ {
+ md5_uint32 *cwp = correct_words;
+ md5_uint32 A_save = A;
+ md5_uint32 B_save = B;
+ md5_uint32 C_save = C;
+ md5_uint32 D_save = D;
+
+ /* First round: using the given function, the context and a constant
+ the next context is computed. Because the algorithms processing
+ unit is a 32-bit word and it is determined to work on words in
+ little endian byte order we perhaps have to change the byte order
+ before the computation. To reduce the work for the next steps
+ we store the swapped words in the array CORRECT_WORDS. */
+
+#define OP(a, b, c, d, s, T) \
+ do \
+ { \
+ a += FF (b, c, d) + (*cwp++ = SWAP (*words)) + T; \
+ ++words; \
+ CYCLIC (a, s); \
+ a += b; \
+ } \
+ while (0)
+
+ /* It is unfortunate that C does not provide an operator for
+ cyclic rotation. Hope the C compiler is smart enough. */
+#define CYCLIC(w, s) (w = (w << s) | (w >> (32 - s)))
+
+ /* Before we start, one word to the strange constants.
+ They are defined in RFC 1321 as
+
+ T[i] = (int) (4294967296.0 * fabs (sin (i))), i=1..64
+ */
+
+ /* Round 1. */
+ OP (A, B, C, D, 7, 0xd76aa478);
+ OP (D, A, B, C, 12, 0xe8c7b756);
+ OP (C, D, A, B, 17, 0x242070db);
+ OP (B, C, D, A, 22, 0xc1bdceee);
+ OP (A, B, C, D, 7, 0xf57c0faf);
+ OP (D, A, B, C, 12, 0x4787c62a);
+ OP (C, D, A, B, 17, 0xa8304613);
+ OP (B, C, D, A, 22, 0xfd469501);
+ OP (A, B, C, D, 7, 0x698098d8);
+ OP (D, A, B, C, 12, 0x8b44f7af);
+ OP (C, D, A, B, 17, 0xffff5bb1);
+ OP (B, C, D, A, 22, 0x895cd7be);
+ OP (A, B, C, D, 7, 0x6b901122);
+ OP (D, A, B, C, 12, 0xfd987193);
+ OP (C, D, A, B, 17, 0xa679438e);
+ OP (B, C, D, A, 22, 0x49b40821);
+
+ /* For the second to fourth round we have the possibly swapped words
+ in CORRECT_WORDS. Redefine the macro to take an additional first
+ argument specifying the function to use. */
+#undef OP
+#define OP(f, a, b, c, d, k, s, T) \
+ do \
+ { \
+ a += f (b, c, d) + correct_words[k] + T; \
+ CYCLIC (a, s); \
+ a += b; \
+ } \
+ while (0)
+
+ /* Round 2. */
+ OP (FG, A, B, C, D, 1, 5, 0xf61e2562);
+ OP (FG, D, A, B, C, 6, 9, 0xc040b340);
+ OP (FG, C, D, A, B, 11, 14, 0x265e5a51);
+ OP (FG, B, C, D, A, 0, 20, 0xe9b6c7aa);
+ OP (FG, A, B, C, D, 5, 5, 0xd62f105d);
+ OP (FG, D, A, B, C, 10, 9, 0x02441453);
+ OP (FG, C, D, A, B, 15, 14, 0xd8a1e681);
+ OP (FG, B, C, D, A, 4, 20, 0xe7d3fbc8);
+ OP (FG, A, B, C, D, 9, 5, 0x21e1cde6);
+ OP (FG, D, A, B, C, 14, 9, 0xc33707d6);
+ OP (FG, C, D, A, B, 3, 14, 0xf4d50d87);
+ OP (FG, B, C, D, A, 8, 20, 0x455a14ed);
+ OP (FG, A, B, C, D, 13, 5, 0xa9e3e905);
+ OP (FG, D, A, B, C, 2, 9, 0xfcefa3f8);
+ OP (FG, C, D, A, B, 7, 14, 0x676f02d9);
+ OP (FG, B, C, D, A, 12, 20, 0x8d2a4c8a);
+
+ /* Round 3. */
+ OP (FH, A, B, C, D, 5, 4, 0xfffa3942);
+ OP (FH, D, A, B, C, 8, 11, 0x8771f681);
+ OP (FH, C, D, A, B, 11, 16, 0x6d9d6122);
+ OP (FH, B, C, D, A, 14, 23, 0xfde5380c);
+ OP (FH, A, B, C, D, 1, 4, 0xa4beea44);
+ OP (FH, D, A, B, C, 4, 11, 0x4bdecfa9);
+ OP (FH, C, D, A, B, 7, 16, 0xf6bb4b60);
+ OP (FH, B, C, D, A, 10, 23, 0xbebfbc70);
+ OP (FH, A, B, C, D, 13, 4, 0x289b7ec6);
+ OP (FH, D, A, B, C, 0, 11, 0xeaa127fa);
+ OP (FH, C, D, A, B, 3, 16, 0xd4ef3085);
+ OP (FH, B, C, D, A, 6, 23, 0x04881d05);
+ OP (FH, A, B, C, D, 9, 4, 0xd9d4d039);
+ OP (FH, D, A, B, C, 12, 11, 0xe6db99e5);
+ OP (FH, C, D, A, B, 15, 16, 0x1fa27cf8);
+ OP (FH, B, C, D, A, 2, 23, 0xc4ac5665);
+
+ /* Round 4. */
+ OP (FI, A, B, C, D, 0, 6, 0xf4292244);
+ OP (FI, D, A, B, C, 7, 10, 0x432aff97);
+ OP (FI, C, D, A, B, 14, 15, 0xab9423a7);
+ OP (FI, B, C, D, A, 5, 21, 0xfc93a039);
+ OP (FI, A, B, C, D, 12, 6, 0x655b59c3);
+ OP (FI, D, A, B, C, 3, 10, 0x8f0ccc92);
+ OP (FI, C, D, A, B, 10, 15, 0xffeff47d);
+ OP (FI, B, C, D, A, 1, 21, 0x85845dd1);
+ OP (FI, A, B, C, D, 8, 6, 0x6fa87e4f);
+ OP (FI, D, A, B, C, 15, 10, 0xfe2ce6e0);
+ OP (FI, C, D, A, B, 6, 15, 0xa3014314);
+ OP (FI, B, C, D, A, 13, 21, 0x4e0811a1);
+ OP (FI, A, B, C, D, 4, 6, 0xf7537e82);
+ OP (FI, D, A, B, C, 11, 10, 0xbd3af235);
+ OP (FI, C, D, A, B, 2, 15, 0x2ad7d2bb);
+ OP (FI, B, C, D, A, 9, 21, 0xeb86d391);
+
+ /* Add the starting values of the context. */
+ A += A_save;
+ B += B_save;
+ C += C_save;
+ D += D_save;
+ }
+
+ /* Put checksum in context given as argument. */
+ ctx->A = A;
+ ctx->B = B;
+ ctx->C = C;
+ ctx->D = D;
+}
diff --git a/source/blender/imbuf/intern/md5.h b/source/blender/imbuf/intern/md5.h
new file mode 100644
index 00000000000..ed38c192d2b
--- /dev/null
+++ b/source/blender/imbuf/intern/md5.h
@@ -0,0 +1,115 @@
+/* md5.h - Declaration of functions and data types used for MD5 sum
+ computing library functions.
+ Copyright (C) 1995 Free Software Foundation, Inc.
+
+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, 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
+
+#ifndef _MD5_H
+#define _MD5_H
+
+#include <stdio.h>
+
+#if defined HAVE_LIMITS_H || _LIBC
+# include <limits.h>
+#endif
+
+/* The following contortions are an attempt to use the C preprocessor
+ to determine an unsigned integral type that is 32 bits wide. An
+ alternative approach is to use autoconf's AC_CHECK_SIZEOF macro, but
+ doing that would require that the configure script compile and *run*
+ the resulting executable. Locally running cross-compiled executables
+ is usually not possible. */
+
+#if defined __STDC__ && __STDC__
+# define UINT_MAX_32_BITS 4294967295U
+#else
+# define UINT_MAX_32_BITS 0xFFFFFFFF
+#endif
+
+/* If UINT_MAX isn't defined, assume it's a 32-bit type.
+ This should be valid for all systems GNU cares about because
+ that doesn't include 16-bit systems, and only modern systems
+ (that certainly have <limits.h>) have 64+-bit integral types. */
+
+#ifndef UINT_MAX
+# define UINT_MAX UINT_MAX_32_BITS
+#endif
+
+#if UINT_MAX == UINT_MAX_32_BITS
+ typedef unsigned int md5_uint32;
+#else
+# if USHRT_MAX == UINT_MAX_32_BITS
+ typedef unsigned short md5_uint32;
+# else
+# if ULONG_MAX == UINT_MAX_32_BITS
+ typedef unsigned long md5_uint32;
+# else
+ /* The following line is intended to evoke an error.
+ Using #error is not portable enough. */
+ "Cannot determine unsigned 32-bit data type."
+# endif
+# endif
+#endif
+
+#undef __P
+#if defined (__STDC__) && __STDC__
+#define __P(x) x
+#else
+#define __P(x) ()
+#endif
+
+/* Structure to save state of computation between the single steps. */
+struct md5_ctx
+{
+ md5_uint32 A;
+ md5_uint32 B;
+ md5_uint32 C;
+ md5_uint32 D;
+};
+
+/*
+ * The following three functions are build up the low level used in
+ * the functions `md5_stream' and `md5_buffer'.
+ */
+
+/* Initialize structure containing state of computation.
+ (RFC 1321, 3.3: Step 3) */
+void md5_init_ctx __P ((struct md5_ctx *ctx));
+
+/* Starting with the result of former calls of this function (or the
+ initialzation function update the context for the next LEN bytes
+ starting at BUFFER.
+ It is necessary that LEN is a multiple of 64!!! */
+void md5_process_block __P ((const void *buffer, size_t len,
+ struct md5_ctx *ctx));
+
+/* Put result from CTX in first 16 bytes following RESBUF. The result is
+ always in little endian byte order, so that a byte-wise output yields
+ to the wanted ASCII representation of the message digest. */
+void *md5_read_ctx __P ((const struct md5_ctx *ctx, void *resbuf));
+
+
+/* Compute MD5 message digest for bytes read from STREAM. The
+ resulting message digest number will be written into the 16 bytes
+ beginning at RESBLOCK. */
+int md5_stream __P ((FILE *stream, void *resblock));
+
+/* Compute MD5 message digest for LEN bytes beginning at BUFFER. The
+ result is always in little endian byte order, so that a byte-wise
+ output yields to the wanted ASCII representation of the message
+ digest. */
+void *md5_buffer __P ((const char *buffer, size_t len, void *resblock));
+
+#endif
diff --git a/source/blender/imbuf/intern/png.c b/source/blender/imbuf/intern/png.c
index 46c5232a61a..bb48ff71bff 100644
--- a/source/blender/imbuf/intern/png.c
+++ b/source/blender/imbuf/intern/png.c
@@ -43,6 +43,7 @@
#include "IMB_allocimbuf.h"
#include "IMB_cmap.h"
+#include "IMB_imginfo.h"
#include "IMB_png.h"
typedef struct PNGReadStruct {
@@ -100,6 +101,7 @@ short imb_savepng(struct ImBuf *ibuf, char *name, int flags)
{
png_structp png_ptr;
png_infop info_ptr;
+
unsigned char *pixels = 0;
unsigned char *from, *to;
png_bytepp row_pointers = 0;
@@ -219,6 +221,33 @@ short imb_savepng(struct ImBuf *ibuf, char *name, int flags)
PNG_COMPRESSION_TYPE_DEFAULT,
PNG_FILTER_TYPE_DEFAULT);
+ /* image text info */
+ if (ibuf->img_info) {
+ png_text* imginfo;
+ ImgInfo* iptr;
+ int num_text = 0;
+ iptr = ibuf->img_info;
+ while (iptr) {
+ num_text++;
+ iptr = iptr->next;
+ }
+
+ imginfo = MEM_callocN(num_text*sizeof(png_text), "png_imginfo");
+ iptr = ibuf->img_info;
+ num_text = 0;
+ while (iptr) {
+ imginfo[num_text].compression = PNG_TEXT_COMPRESSION_NONE;
+ imginfo[num_text].key = iptr->key;
+ imginfo[num_text].text = iptr->value;
+ num_text++;
+ iptr = iptr->next;
+ }
+
+ png_set_text(png_ptr, info_ptr, imginfo, num_text);
+ MEM_freeN(imginfo);
+
+ }
+
// write the file header information
png_write_info(png_ptr, info_ptr);
@@ -409,6 +438,15 @@ struct ImBuf *imb_loadpng(unsigned char *mem, int size, int flags)
break;
}
+ if (flags & IB_imginfo) {
+ png_text* text_chunks;
+ int count = png_get_text(png_ptr, info_ptr, &text_chunks, NULL);
+ for(i = 0; i < count; i++) {
+ IMB_imginfo_add_field(ibuf, text_chunks[i].key, text_chunks[i].text);
+ ibuf->flags |= IB_imginfo;
+ }
+ }
+
png_read_end(png_ptr, info_ptr);
}
diff --git a/source/blender/imbuf/intern/thumbs.c b/source/blender/imbuf/intern/thumbs.c
new file mode 100644
index 00000000000..6976aff6b39
--- /dev/null
+++ b/source/blender/imbuf/intern/thumbs.c
@@ -0,0 +1,457 @@
+/**
+ * $Id: $
+ *
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2007 Blender Foundation
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): Andrea Weikert.
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+#include "BKE_global.h"
+#include "BKE_utildefines.h"
+#include "BLI_blenlib.h"
+#include "MEM_guardedalloc.h"
+
+#include "IMB_imbuf_types.h"
+#include "IMB_imbuf.h"
+#include "IMB_thumbs.h"
+#include "IMB_imginfo.h"
+
+
+#include "md5.h"
+
+#ifdef WIN32
+#include <windows.h> /* need to include windows.h so _WIN32_IE is defined */
+#ifndef _WIN32_IE
+#define _WIN32_IE 0x0400 /* minimal requirements for SHGetSpecialFolderPath on MINGW MSVC has this defined already */
+#endif
+#include <shlobj.h> /* for SHGetSpecialFolderPath, has to be done before BLI_winstuff because 'near' is disabled through BLI_windstuff */
+#include "BLI_winstuff.h"
+#include <process.h> /* getpid */
+#else
+#include <unistd.h>
+#endif
+
+#include <stdlib.h>
+#include <string.h>
+#include <stdio.h>
+#include <time.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <stdio.h>
+
+#define URI_MAX FILE_MAX*3 + 8
+
+static int get_thumb_dir( char* dir , ThumbSize size)
+{
+ char* home;
+
+#ifdef WIN32
+ /* yes, applications shouldn't store data there, but so does GIMP :)*/
+ SHGetSpecialFolderPath(0, dir, CSIDL_PROFILE, 0);
+#else
+ home = getenv("HOME");
+ if (!home) return 0;
+ BLI_strncpy(dir, home, FILE_MAX);
+#endif
+ switch(size) {
+ case THB_NORMAL:
+ strcat(dir, "/.thumbnails/normal");
+ break;
+ case THB_LARGE:
+ strcat(dir, "/.thumbnails/large");
+ break;
+ case THB_FAIL:
+ strcat(dir, "/.thumbnails/fail/blender");
+ break;
+ default:
+ return 0; /* unknown size */
+ }
+ BLI_cleanup_dir(G.sce, dir);
+ return 1;
+}
+
+/** ----- begin of adapted code from glib ---
+ * The following code is adapted from function g_escape_uri_string from the gnome glib
+ * Source: http://svn.gnome.org/viewcvs/glib/trunk/glib/gconvert.c?view=markup
+ * released under the Gnu General Public License.
+ */
+typedef enum {
+ UNSAFE_ALL = 0x1, /* Escape all unsafe characters */
+ UNSAFE_ALLOW_PLUS = 0x2, /* Allows '+' */
+ UNSAFE_PATH = 0x8, /* Allows '/', '&', '=', ':', '@', '+', '$' and ',' */
+ UNSAFE_HOST = 0x10, /* Allows '/' and ':' and '@' */
+ UNSAFE_SLASHES = 0x20 /* Allows all characters except for '/' and '%' */
+} UnsafeCharacterSet;
+
+static const unsigned char acceptable[96] = {
+ /* A table of the ASCII chars from space (32) to DEL (127) */
+ /* ! " # $ % & ' ( ) * + , - . / */
+ 0x00,0x3F,0x20,0x20,0x28,0x00,0x2C,0x3F,0x3F,0x3F,0x3F,0x2A,0x28,0x3F,0x3F,0x1C,
+ /* 0 1 2 3 4 5 6 7 8 9 : ; < = > ? */
+ 0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x38,0x20,0x20,0x2C,0x20,0x20,
+ /* @ A B C D E F G H I J K L M N O */
+ 0x38,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,
+ /* P Q R S T U V W X Y Z [ \ ] ^ _ */
+ 0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x20,0x20,0x20,0x20,0x3F,
+ /* ` a b c d e f g h i j k l m n o */
+ 0x20,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,
+ /* p q r s t u v w x y z { | } ~ DEL */
+ 0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x20,0x20,0x20,0x3F,0x20
+};
+
+static const char hex[16] = "0123456789abcdef";
+
+/* Note: This escape function works on file: URIs, but if you want to
+ * escape something else, please read RFC-2396 */
+void escape_uri_string (const char *string, char* escaped_string, int len,UnsafeCharacterSet mask)
+{
+#define ACCEPTABLE(a) ((a)>=32 && (a)<128 && (acceptable[(a)-32] & use_mask))
+
+ const char *p;
+ char *q;
+ int c;
+ UnsafeCharacterSet use_mask;
+ use_mask = mask;
+
+ for (q = escaped_string, p = string; (*p != '\0') && len; p++) {
+ c = (unsigned char) *p;
+ len--;
+
+ if (!ACCEPTABLE (c)) {
+ *q++ = '%'; /* means hex coming */
+ *q++ = hex[c >> 4];
+ *q++ = hex[c & 15];
+ } else {
+ *q++ = *p;
+ }
+ }
+
+ *q = '\0';
+}
+
+void to_hex_char(char* hexbytes, const unsigned char* bytes, int len)
+{
+ const unsigned char *p;
+ char *q;
+
+ for (q = hexbytes, p = bytes; len; p++) {
+ const unsigned char c = (unsigned char) *p;
+ len--;
+ *q++ = hex[c >> 4];
+ *q++ = hex[c & 15];
+ }
+}
+
+/** ----- end of adapted code from glib --- */
+
+static int uri_from_filename( const char *dir, const char *file, char *uri )
+{
+ char orig_uri[URI_MAX];
+ const char* dirstart = dir;
+
+#ifdef WIN32
+ {
+ char vol[3];
+
+ BLI_strncpy(orig_uri, "file:///", FILE_MAX);
+ if (strlen(dir) < 2 && dir[1] != ':') {
+ /* not a correct absolute path */
+ return 0;
+ }
+ /* on windows, using always uppercase drive/volume letter in uri */
+ vol[0] = toupper(dir[0]);
+ vol[1] = ':';
+ vol[2] = '\0';
+ strcat(orig_uri, vol);
+ dirstart += 2;
+ }
+#else
+ BLI_strncpy(orig_uri, "file://", FILE_MAX);
+#endif
+ strcat(orig_uri, dirstart);
+ strcat(orig_uri, file);
+ BLI_char_switch(orig_uri, '\\', '/');
+
+#ifdef WITH_ICONV
+ {
+ escape_uri_string(orig_uri, uri_utf8, FILE_MAX*3+8, UNSAFE_PATH);
+ BLI_string_to_utf8(uri_utf8, uri, NULL);
+ char uri_utf8[FILE_MAX*3+8];
+ }
+#else
+ escape_uri_string(orig_uri, uri, FILE_MAX*3+8, UNSAFE_PATH);
+#endif
+ return 1;
+}
+
+static void thumbname_from_uri(const char* uri, char* thumb)
+{
+ char hexdigest[33];
+ unsigned char digest[16];
+
+ md5_buffer( uri, strlen(uri), digest);
+ hexdigest[0] = '\0';
+ to_hex_char(hexdigest, digest, 16);
+ hexdigest[32] = '\0';
+ sprintf(thumb, "%s.png", hexdigest);
+}
+
+static int thumbpath_from_uri(const char* uri, char* path, ThumbSize size)
+{
+ char tmppath[FILE_MAX];
+ int rv = 0;
+
+ if (get_thumb_dir(tmppath, size)) {
+ char thumb[40];
+ thumbname_from_uri(uri, thumb);
+ BLI_snprintf(path, FILE_MAX, "%s%s", tmppath, thumb);
+ rv = 1;
+ }
+ return rv;
+}
+
+
+/* create thumbnail for file and returns new imbuf for thumbnail */
+ImBuf* IMB_thumb_create(const char* dir, const char* file, ThumbSize size, ThumbSource source)
+{
+ ImBuf *img = 0;
+ char uri[URI_MAX];
+ char desc[URI_MAX+22];
+ char tpath[FILE_MAX];
+ char tdir[FILE_MAX];
+ char wdir[FILE_MAX];
+ char temp[FILE_MAX];
+ char mtime[40];
+ char cwidth[40];
+ char cheight[40];
+ char thumb[40];
+ short tsize = 128;
+ short ex, ey;
+ float scaledx, scaledy;
+ struct stat info;
+
+ switch(size) {
+ case THB_NORMAL:
+ tsize = 128;
+ break;
+ case THB_LARGE:
+ tsize = 256;
+ break;
+ case THB_FAIL:
+ tsize = 0;
+ break;
+ default:
+ return 0; /* unknown size */
+ }
+
+ uri_from_filename(dir, file,uri);
+ thumbname_from_uri(uri, thumb);
+ if (get_thumb_dir(tdir, size)) {
+ BLI_snprintf(tpath, FILE_MAX, "%s%s", tdir, thumb);
+ thumb[8] = '\0'; /* shorten for tempname, not needed anymore */
+ BLI_snprintf(temp, FILE_MAX, "%sblender_%d_%s.png", tdir, abs(getpid()), thumb);
+ if (strncmp(thumb, dir, strlen(dir)) == 0) {
+ return NULL;
+ }
+ if (size == THB_FAIL) {
+ img = IMB_allocImBuf(0,0,32, IB_rect | IB_imginfo, 0);
+ if (!img) return 0;
+ } else {
+ if (THB_SOURCE_IMAGE == source) {
+ BLI_getwdN(wdir);
+ chdir(dir);
+ img = IMB_loadiffname(file, IB_rect);
+ stat(file, &info);
+ sprintf(mtime, "%ld", info.st_mtime);
+ sprintf(cwidth, "%d", img->x);
+ sprintf(cheight, "%d", img->y);
+ chdir(wdir);
+ } else if (THB_SOURCE_MOVIE == source) {
+ struct anim * anim = NULL;
+ BLI_getwdN(wdir);
+ chdir(dir);
+ anim = IMB_open_anim(file, IB_rect | IB_imginfo);
+ if (anim != NULL) {
+ img = IMB_anim_absolute(anim, 0);
+ if (img == NULL) {
+ printf("not an anim; %s\n", file);
+ } else {
+ IMB_freeImBuf(img);
+ img = IMB_anim_previewframe(anim);
+ }
+ IMB_free_anim(anim);
+ }
+ stat(file, &info);
+ sprintf(mtime, "%ld", info.st_mtime);
+ chdir(wdir);
+ }
+ if (!img) return 0;
+
+ if (img->x > img->y) {
+ scaledx = (float)tsize;
+ scaledy = ( (float)img->y/(float)img->x )*tsize;
+ }
+ else {
+ scaledy = (float)tsize;
+ scaledx = ( (float)img->x/(float)img->y )*tsize;
+ }
+ ex = (short)scaledx;
+ ey = (short)scaledy;
+
+ IMB_scaleImBuf(img, ex, ey);
+ }
+ sprintf(desc, "Thumbnail for %s", uri);
+ IMB_imginfo_add_field(img, "Description", desc);
+ IMB_imginfo_add_field(img, "Software", "Blender");
+ IMB_imginfo_add_field(img, "Thumb::URI", uri);
+ IMB_imginfo_add_field(img, "Thumb::MTime", mtime);
+ if (THB_SOURCE_IMAGE == source) {
+ IMB_imginfo_add_field(img, "Thumb::Image::Width", cwidth);
+ IMB_imginfo_add_field(img, "Thumb::Image::Height", cheight);
+ }
+ img->ftype = PNG;
+ img->depth = 32;
+ if (IMB_saveiff(img, temp, IB_rect | IB_imginfo)) {
+#ifndef WIN32
+ chmod(temp, S_IRUSR | S_IWUSR);
+#endif
+ BLI_rename(temp, tpath);
+ }
+
+ return img;
+ }
+ return img;
+}
+
+/* read thumbnail for file and returns new imbuf for thumbnail */
+ImBuf* IMB_thumb_read(const char* dir, const char* file, ThumbSize size)
+{
+ char thumb[FILE_MAX];
+ char uri[FILE_MAX*3+8];
+ ImBuf *img = 0;
+
+ if (!uri_from_filename(dir, file,uri)) {
+ return NULL;
+ }
+ if (thumbpath_from_uri(uri, thumb, size)) {
+ img = IMB_loadiffname(thumb, IB_rect | IB_imginfo);
+ }
+
+ return img;
+}
+
+/* delete all thumbs for the file */
+void IMB_thumb_delete(const char* dir, const char* file, ThumbSize size)
+{
+ char thumb[FILE_MAX];
+ char uri[FILE_MAX*3+8];
+
+ if (!uri_from_filename(dir, file,uri)) {
+ return;
+ }
+ if (thumbpath_from_uri(uri, thumb, size)) {
+ if (strncmp(thumb, dir, strlen(dir)) == 0) {
+ return;
+ }
+ if (BLI_exists(thumb)) {
+ BLI_delete(thumb, 0, 0);
+ }
+ }
+}
+
+
+/* create the thumb if necessary and manage failed and old thumbs */
+ImBuf* IMB_thumb_manage(const char* dir, const char* file, ThumbSize size, ThumbSource source)
+{
+ char path[FILE_MAX];
+ char thumb[FILE_MAX];
+ char uri[FILE_MAX*3+8];
+ struct stat st;
+ ImBuf* img = NULL;
+
+ BLI_join_dirfile(path, dir, file);
+ if (stat(path, &st)) {
+ return NULL;
+ }
+ if (!uri_from_filename(dir, file,uri)) {
+ return NULL;
+ }
+ if (thumbpath_from_uri(uri, thumb, THB_FAIL)) {
+ /* failure thumb exists, don't try recreating */
+ if (BLI_exists(thumb)) {
+ return NULL;
+ }
+ }
+
+ if (thumbpath_from_uri(uri, thumb, size)) {
+ if (strncmp(thumb, dir, strlen(dir)) == 0) {
+ img = IMB_loadiffname(path, IB_rect);
+ } else {
+ img = IMB_loadiffname(thumb, IB_rect | IB_imginfo);
+ if (img) {
+ char mtime[40];
+ if (!IMB_imginfo_get_field(img, "Thumb::MTime", mtime, 40)) {
+ /* illegal thumb, forget it! */
+ IMB_freeImBuf(img);
+ img = 0;
+ } else {
+ time_t t = atol(mtime);
+ if (st.st_mtime != t) {
+ /* recreate all thumbs */
+ IMB_freeImBuf(img);
+ img = 0;
+ IMB_thumb_delete(dir, file, THB_NORMAL);
+ IMB_thumb_delete(dir, file, THB_LARGE);
+ IMB_thumb_delete(dir, file, THB_FAIL);
+ img = IMB_thumb_create(dir, file, size, source);
+ if(!img){
+ /* thumb creation failed, write fail thumb */
+ img = IMB_thumb_create(dir, file, THB_FAIL, source);
+ if (img) {
+ /* we don't need failed thumb anymore */
+ IMB_freeImBuf(img);
+ img = 0;
+ }
+ }
+ }
+ }
+ } else {
+ img = IMB_thumb_create(dir, file, size, source);
+ if(!img){
+ /* thumb creation failed, write fail thumb */
+ img = IMB_thumb_create(dir, file, THB_FAIL, source);
+ if (img) {
+ /* we don't need failed thumb anymore */
+ IMB_freeImBuf(img);
+ img = 0;
+ }
+ }
+ }
+ }
+ }
+
+ return img;
+}
+
+
diff --git a/source/blender/include/BIF_filelist.h b/source/blender/include/BIF_filelist.h
new file mode 100644
index 00000000000..a8d8e6f9445
--- /dev/null
+++ b/source/blender/include/BIF_filelist.h
@@ -0,0 +1,87 @@
+/**
+ * $Id: $
+ *
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * 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. The Blender
+ * Foundation also sells licenses for use in proprietary software under
+ * the Blender License. See http://www.blender.org/BL/ for information
+ * about this.
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2007 Blender Foundation.
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): none yet.
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+#ifndef BIF_FILELIST_H
+#define BIF_FILELIST_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct FileList;
+struct direntry;
+struct BlendHandle;
+
+struct FileList * BIF_filelist_new();
+void BIF_filelist_init_icons();
+void BIF_filelist_free_icons();
+struct FileList * BIF_filelist_copy(struct FileList* filelist);
+int BIF_filelist_find(struct FileList* filelist, char *file);
+void BIF_filelist_free(struct FileList* filelist);
+void BIF_filelist_freelib(struct FileList* filelist);
+void BIF_filelist_sort(struct FileList* filelist, short sort);
+int BIF_filelist_numfiles(struct FileList* filelist);
+const char * BIF_filelist_dir(struct FileList* filelist);
+void BIF_filelist_setdir(struct FileList* filelist, const char *dir);
+void BIF_filelist_appenddir(struct FileList* filelist, const char *relname);
+struct direntry * BIF_filelist_file(struct FileList* filelist, int index);
+void BIF_filelist_hidedot(struct FileList* filelist, short hide);
+void BIF_filelist_setfilter(struct FileList* filelist, unsigned int filter);
+void BIF_filelist_filter(struct FileList* filelist);
+void BIF_filelist_swapselect(struct FileList* filelist);
+void BIF_filelist_imgsize(struct FileList* filelist, short w, short h);
+void BIF_filelist_loadimage(struct FileList* filelist, int index);
+struct ImBuf * BIF_filelist_getimage(struct FileList* filelist, int index);
+
+void BIF_filelist_readdir(struct FileList* filelist);
+
+int BIF_filelist_empty(struct FileList* filelist);
+void BIF_filelist_parent(struct FileList* filelist);
+void BIF_filelist_setfiletypes(struct FileList* filelist, short has_quicktime);
+int BIF_filelist_islibrary (struct FileList* filelist, char* dir, char* group);
+void BIF_filelist_from_main(struct FileList* filelist);
+void BIF_filelist_from_library(struct FileList* filelist);
+void BIF_filelist_append_library(struct FileList* filelist, char *dir, char* file, short flag, int idcode);
+void BIF_filelist_settype(struct FileList* filelist, int type);
+short BIF_filelist_gettype(struct FileList* filelist);
+void BIF_filelist_setipotype(struct FileList* filelist, short ipotype);
+void BIF_filelist_hasfunc(struct FileList* filelist, int has_func);
+
+struct BlendHandle *BIF_filelist_lib(struct FileList* filelist);
+int BIF_groupname_to_code(char *group); /* TODO: where should this go */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+
diff --git a/source/blender/include/BIF_fsmenu.h b/source/blender/include/BIF_fsmenu.h
index b32dee01854..1c5280c14f8 100644
--- a/source/blender/include/BIF_fsmenu.h
+++ b/source/blender/include/BIF_fsmenu.h
@@ -55,17 +55,20 @@ char* fsmenu_build_menu (void);
/** Append a seperator to the FSMenu, inserts always follow the
* last seperator.
*/
-void fsmenu_append_seperator (void);
+void fsmenu_append_separator (void);
/** Inserts a new fsmenu entry with the given @a path.
* Duplicate entries are not added.
* @param sorted Should entry be inserted in sorted order?
*/
-void fsmenu_insert_entry (char *path, int sorted);
+void fsmenu_insert_entry (char *path, int sorted, short save);
/** Removes the fsmenu entry at the given @a index. */
void fsmenu_remove_entry (int index);
+ /** saves the 'favourites' to the specified file */
+void fsmenu_write_file(const char *filename);
+
/** Free's all the memory associated with the fsmenu */
void fsmenu_free (void);
diff --git a/source/blender/include/BIF_imasel.h b/source/blender/include/BIF_imasel.h
index d6a1800730b..0e92abe14e4 100644
--- a/source/blender/include/BIF_imasel.h
+++ b/source/blender/include/BIF_imasel.h
@@ -33,28 +33,19 @@
#define BIF_IMASEL_H
struct SpaceImaSel;
-struct OneSelectableIma;
struct ScrArea;
-struct ImaDir;
-void imadir_parent(struct SpaceImaSel *simasel);
-int bitset(int l, int bit);
-void free_sel_ima(struct OneSelectableIma *firstima);
-
-void write_new_pib(struct SpaceImaSel *simasel);
-void free_ima_dir(struct ImaDir *firstdir);
-void check_for_pib(struct SpaceImaSel *simasel);
-void clear_ima_dir(struct SpaceImaSel *simasel);
-void check_ima_dir_name(char *dir);
-int get_ima_dir(char *dirname, int dtype, int *td, struct ImaDir **first);
-void get_next_image(struct SpaceImaSel *simasel);
-void get_file_info(struct SpaceImaSel *simasel);
-void get_pib_file(struct SpaceImaSel *simasel);
-void change_imadir(struct SpaceImaSel *simasel);
-void check_imasel_copy(struct SpaceImaSel *simasel);
void free_imasel(struct SpaceImaSel *simasel);
void clever_numbuts_imasel(void);
+void activate_imageselect(int type, char *title, char *file, void (*func)(char *));
+void activate_imageselect_menu(int type, char *title, char *file, char *pupmenu, short *menup, void (*func)(char *));
+void activate_imageselect_args(int type, char *title, char *file, void (*func)(char *, void *, void *), void *arg1, void *arg2);
+
+void activate_databrowse_imasel(struct ID *id, int idcode, int fromcode, int retval, short *menup, void (*func)(unsigned short));
+/*
+void activate_databrowse_imasel_args(struct ID *id, int idcode, int fromcode, short *menup, void (*func)(char *, void *, void *), void *arg1, void *arg2);
+*/
#endif
diff --git a/source/blender/include/BIF_interface_icons.h b/source/blender/include/BIF_interface_icons.h
index c69fa122099..c628d68e9db 100644
--- a/source/blender/include/BIF_interface_icons.h
+++ b/source/blender/include/BIF_interface_icons.h
@@ -48,6 +48,7 @@ typedef struct IconFile {
#define ICON_DEFAULT_HEIGHT 16
+#define PREVIEW_DEFAULT_HEIGHT 96
/*
Resizable Icons for Blender
@@ -57,6 +58,8 @@ int BIF_icon_get_width(int icon_id);
int BIF_icon_get_height(int icon_id);
void BIF_icon_draw(float x, float y, int icon_id);
+void BIF_icon_draw_preview(float x, float y, int icon_id, int nocreate);
+
void BIF_icon_draw_aspect(float x, float y, int icon_id, float aspect);
void BIF_icon_draw_aspect_blended(float x, float y, int icon_id, float aspect, int shade);
void BIF_icons_free();
diff --git a/source/blender/include/BIF_resources.h b/source/blender/include/BIF_resources.h
index 77c0f5861e3..d734e59046f 100644
--- a/source/blender/include/BIF_resources.h
+++ b/source/blender/include/BIF_resources.h
@@ -164,7 +164,7 @@ typedef enum {
ICON_FACESEL_DEHLT,
ICON_FACESEL_HLT,
ICON_EDIT_DEHLT,
- ICON_BLANK19,
+ ICON_BOOKMARKS,
ICON_BLANK20,
ICON_BLANK21,
ICON_BLANK22,
diff --git a/source/blender/include/BIF_space.h b/source/blender/include/BIF_space.h
index 884f0459abf..12f1e1586a0 100644
--- a/source/blender/include/BIF_space.h
+++ b/source/blender/include/BIF_space.h
@@ -75,6 +75,9 @@ struct SpaceOops;
/* sequence handler codes */
#define SEQ_HANDLER_PROPERTIES 60
+/* imasel handler codes */
+#define IMASEL_HANDLER_IMAGE 70
+
/* theme codes */
#define B_ADD_THEME 3301
#define B_DEL_THEME 3302
diff --git a/source/blender/include/BSE_drawimasel.h b/source/blender/include/BSE_drawimasel.h
index f412ca08584..6c68ba79bb9 100644
--- a/source/blender/include/BSE_drawimasel.h
+++ b/source/blender/include/BSE_drawimasel.h
@@ -33,27 +33,28 @@
#ifndef BSE_DRAWIMASEL_H
#define BSE_DRAWIMASEL_H
+
+/* button events */
+#define B_FS_FILENAME 1
+#define B_FS_DIRNAME 2
+#define B_FS_DIR_MENU 3
+#define B_FS_PARDIR 4
+#define B_FS_LOAD 5
+#define B_FS_CANCEL 6
+#define B_FS_LIBNAME 7
+#define B_FS_BOOKMARK 8
+
+/* ui geometry */
+#define IMASEL_BUTTONS_HEIGHT 60
+#define TILE_BORDER_X 8
+#define TILE_BORDER_Y 8
+
struct ScrArea;
struct SpaceImaSel;
-void viewgate(short sx, short sy, short ex, short ey);
-void areaview (void);
-void calc_hilite(struct SpaceImaSel *simasel);
-void make_sima_area(struct SpaceImaSel *simasel);
-void draw_sima_area(struct SpaceImaSel *simasel);
-void select_ima_files(struct SpaceImaSel *simasel);
-void move_imadir_sli(struct SpaceImaSel *simasel);
-void move_imafile_sli(struct SpaceImaSel *simasel);
-void ima_select_all(struct SpaceImaSel *simasel);
-void pibplay(struct SpaceImaSel *simasel);
void drawimaselspace(struct ScrArea *sa, void *spacedata);
-
-/* void calc_hilite(SpaceImaSel *simasel); */
-/* void ima_select_all(SpaceImaSel *simasel); */
-/* void move_imadir_sli(SpaceImaSel *simasel); */
-/* void move_imafile_sli(SpaceImaSel *simasel); */
-/* void pibplay(SpaceImaSel *simasel); */
-/* void select_ima_files(SpaceImaSel *simasel); */
+void calc_imasel_rcts(SpaceImaSel *simasel, int winx, int winy);
+void do_imasel_buttonevents(short event, SpaceImaSel *simasel);
#endif /* BSE_DRAWIMASEL_H */
diff --git a/source/blender/include/BSE_filesel.h b/source/blender/include/BSE_filesel.h
index 6934899062e..a41eea32040 100644
--- a/source/blender/include/BSE_filesel.h
+++ b/source/blender/include/BSE_filesel.h
@@ -53,8 +53,6 @@ void activate_fileselect(int type, char *title, char *file, void (*func)(char *)
void activate_fileselect_menu(int type, char *title, char *file, char *pupmenu, short *menup, void (*func)(char *));
void activate_fileselect_args(int type, char *title, char *file, void (*func)(char *, void *, void *), void *arg1, void *arg2);
-void activate_imageselect(int type, char *title, char *file, void (*func)(char *));
-
void activate_databrowse(struct ID *id, int idcode, int fromcode, int retval, short *menup, void (*func)(unsigned short));
void activate_databrowse_args(struct ID *id, int idcode, int fromcode, short *menup, void (*func)(char *, void *, void *), void *arg1, void *arg2);
diff --git a/source/blender/include/blendef.h b/source/blender/include/blendef.h
index 596b11c609c..349685a5d8a 100644
--- a/source/blender/include/blendef.h
+++ b/source/blender/include/blendef.h
@@ -344,7 +344,10 @@
#define B_CONTEXT_SWITCH 406
/* IMASEL: 450 */
-/* in imasel.h */
+/* in imasel.h - not any more - elubie */
+#define B_SORTIMASELLIST 451
+#define B_RELOADIMASELDIR 452
+#define B_FILTERIMASELDIR 453
/* TEXT: 500 */
#define B_TEXTBROWSE 501
diff --git a/source/blender/include/datatoc.h b/source/blender/include/datatoc.h
index d7a1aa5c78c..7afd4428d70 100644
--- a/source/blender/include/datatoc.h
+++ b/source/blender/include/datatoc.h
@@ -44,6 +44,9 @@ extern char datatoc_Bfs[];
extern int datatoc_blenderbuttons_size;
extern char datatoc_blenderbuttons[];
+extern int datatoc_prvicons_size;
+extern char datatoc_prvicons[];
+
extern int datatoc_Bfont_size;
extern char datatoc_Bfont[];
diff --git a/source/blender/include/interface.h b/source/blender/include/interface.h
index d7be02c6fc5..d8e779b9af8 100644
--- a/source/blender/include/interface.h
+++ b/source/blender/include/interface.h
@@ -230,7 +230,7 @@ extern void ui_draw_but(uiBut *but);
extern void ui_rasterpos_safe(float x, float y, float aspect);
extern void ui_draw_tria_icon(float x, float y, float aspect, char dir);
extern void ui_draw_anti_x(float x1, float y1, float x2, float y2);
-
+extern void ui_dropshadow(rctf *rct, float radius, float aspect, int select);
#endif
diff --git a/source/blender/makesdna/DNA_ID.h b/source/blender/makesdna/DNA_ID.h
index f8ad5399af3..d939d0dc879 100644
--- a/source/blender/makesdna/DNA_ID.h
+++ b/source/blender/makesdna/DNA_ID.h
@@ -120,6 +120,18 @@ typedef struct Library {
struct Library *parent; /* for outliner, showing dependency */
} Library;
+#define PREVIEW_MIPMAPS 2
+#define PREVIEW_MIPMAP_ZERO 0
+#define PREVIEW_MIPMAP_LARGE 1
+
+typedef struct PreviewImage {
+ unsigned int w[2];
+ unsigned int h[2];
+ short changed[2];
+ short pad0, pad1;
+ unsigned int * rect[2];
+} PreviewImage;
+
/**
* Defines for working with IDs.
*
diff --git a/source/blender/makesdna/DNA_image_types.h b/source/blender/makesdna/DNA_image_types.h
index cf13a1116a9..694279d4605 100644
--- a/source/blender/makesdna/DNA_image_types.h
+++ b/source/blender/makesdna/DNA_image_types.h
@@ -41,11 +41,6 @@ struct anim;
struct ImBuf;
struct RenderResult;
-typedef struct PreviewImage {
- unsigned int w;
- unsigned int h;
- unsigned int * rect;
-} PreviewImage;
/* ImageUser is in Texture, in Nodes, Background Image, Image Window, .... */
/* should be used in conjunction with an ID * to Image. */
diff --git a/source/blender/makesdna/DNA_lamp_types.h b/source/blender/makesdna/DNA_lamp_types.h
index 104b13ea24c..5d998ccca6e 100644
--- a/source/blender/makesdna/DNA_lamp_types.h
+++ b/source/blender/makesdna/DNA_lamp_types.h
@@ -79,6 +79,9 @@ typedef struct Lamp {
struct MTex *mtex[10];
struct Ipo *ipo;
+ /* preview */
+ struct PreviewImage *preview;
+
ScriptLink scriptlink;
} Lamp;
diff --git a/source/blender/makesdna/DNA_material_types.h b/source/blender/makesdna/DNA_material_types.h
index 0fad110d64b..b6bc475fb28 100644
--- a/source/blender/makesdna/DNA_material_types.h
+++ b/source/blender/makesdna/DNA_material_types.h
@@ -105,7 +105,8 @@ typedef struct Material {
struct bNodeTree *nodetree;
struct Ipo *ipo;
struct Group *group; /* light group */
-
+ struct PreviewImage * preview;
+
/* dynamic properties */
float friction, fh, reflect;
float fhdist, xyfrict;
diff --git a/source/blender/makesdna/DNA_space_types.h b/source/blender/makesdna/DNA_space_types.h
index e70c8baaa78..42f08e3795e 100644
--- a/source/blender/makesdna/DNA_space_types.h
+++ b/source/blender/makesdna/DNA_space_types.h
@@ -52,6 +52,7 @@ struct BlendHandle;
struct RenderInfo;
struct bNodeTree;
struct uiBlock;
+struct FileList;
/**
* The base structure all the other spaces
@@ -336,89 +337,63 @@ typedef struct SpaceNode {
#define SNODE_DO_PREVIEW 1
#define SNODE_BACKDRAW 2
-#
-#
-typedef struct OneSelectableIma {
- int header;
- int ibuf_type;
- struct ImBuf *pict;
- struct OneSelectableIma *next;
- struct OneSelectableIma *prev;
-
- short cmap, image, draw_me, rt;
- short sx, sy, ex, ey, dw, dh;
- short selectable, selected;
- int mtime, disksize;
- char file_name[64];
-
- short orgx, orgy, orgd, anim; /* same as ibuf->x...*/
- char dummy[4]; /* 128 */
-
- char pict_rect[3968]; /* 4096 (RECT = 64 * 62) */
-
-} OneSelectableIma;
-
-#
-#
-typedef struct ImaDir {
- struct ImaDir *next, *prev;
- int selected, hilite;
- int type, size;
- int mtime;
- char name[100];
-} ImaDir;
-
typedef struct SpaceImaSel {
SpaceLink *next, *prev;
int spacetype;
float blockscale;
struct ScrArea *area;
- char title[28];
-
- int fase;
- short mode, subfase;
- short mouse_move_redraw, imafase;
- short mx, my;
-
- short dirsli, dirsli_lines;
- short dirsli_sx, dirsli_ey , dirsli_ex, dirsli_h;
- short imasli, fileselmenuitem;
- short imasli_sx, imasli_ey , imasli_ex, imasli_h;
-
- short dssx, dssy, dsex, dsey;
- short desx, desy, deex, deey;
- short fssx, fssy, fsex, fsey;
- short dsdh, fsdh;
- short fesx, fesy, feex, feey;
- short infsx, infsy, infex, infey;
- short dnsx, dnsy, dnw, dnh;
- short fnsx, fnsy, fnw, fnh;
-
-
- char fole[128], dor[128];
- char file[128], dir[128];
- ImaDir *firstdir, *firstfile;
- int topdir, totaldirs, hilite;
- int topfile, totalfiles;
-
- float image_slider;
- float slider_height;
- float slider_space;
- short topima, totalima;
- short curimax, curimay;
- OneSelectableIma *first_sel_ima;
- OneSelectableIma *hilite_ima;
- short total_selected, ima_redraw;
- int pad2;
+ short blockhandler[8];
+
+ View2D v2d;
+
+ struct FileList *files;
+
+ /* specific stuff for drawing */
+ char title[24];
+ char dir[160];
+ char file[80];
+
+ short type, menu, flag, sort;
+
+ void *curfont;
+ int active_file;
+
+ int numtilesx;
+ int numtilesy;
+
+ int selstate;
+
+ struct rcti viewrect;
+ struct rcti bookmarkrect;
+
+ float scrollpos; /* current position of scrollhandle */
+ float scrollheight; /* height of the scrollhandle */
+ float scrollarea; /* scroll region, scrollpos is from 0 to scrollarea */
+
+ float aspect;
+ unsigned short retval; /* event */
+
+ short ipotype;
- struct ImBuf *cmap;
+ short filter;
+ short active_bookmark;
+ short pad, pad1;
+
+ /* view settings */
+ short prv_w;
+ short prv_h;
+
+ /* one day we'll add unions to dna */
+ void (*returnfunc)(char *);
+ void (*returnfunc_event)(unsigned short);
+ void (*returnfunc_args)(char *, void *, void *);
+
+ void *arg1, *arg2;
+ short *menup; /* pointer to menu result or ID browsing */
+ char *pupmenu; /* optional menu in header */
- /* Also fucked. Needs to change so things compile, but breaks sdna
- * ... */
-/* void (*returnfunc)(void); */
- void (*returnfunc)(char*);
- void *arg1;
+ struct ImBuf *img;
} SpaceImaSel;
@@ -447,7 +422,7 @@ typedef struct SpaceImaSel {
#define FILE_MAIN 2
#define FILE_LOADFONT 3
-/* sfile->flag */
+/* sfile->flag and simasel->flag */
#define FILE_SHOWSHORT 1
#define FILE_STRINGCODE 2
#define FILE_LINK 4
@@ -456,6 +431,8 @@ typedef struct SpaceImaSel {
#define FILE_ACTIVELAY 32
#define FILE_ATCURSOR 64
#define FILE_SYNCPOSE 128
+#define FILE_FILTER 256
+#define FILE_BOOKMARKS 512
/* sfile->sort */
#define FILE_SORTALPHA 0
@@ -472,6 +449,9 @@ typedef struct SpaceImaSel {
#define PYSCRIPTFILE 64
#define FTFONTFILE 128
#define SOUNDFILE 256
+#define TEXTFILE 512
+#define MOVIEFILE_ICON 1024 /* movie file that preview can't load */
+#define FOLDERFILE 2048 /* represents folders for filtering */
#define SCROLLH 16 /* height scrollbar */
#define SCROLLB 16 /* width scrollbar */
diff --git a/source/blender/makesdna/DNA_texture_types.h b/source/blender/makesdna/DNA_texture_types.h
index 4ad92f9f33d..064cfe39d45 100644
--- a/source/blender/makesdna/DNA_texture_types.h
+++ b/source/blender/makesdna/DNA_texture_types.h
@@ -44,6 +44,7 @@ struct EnvMap;
struct Object;
struct Tex;
struct Image;
+struct PreviewImage;
struct ImBuf;
typedef struct MTex {
@@ -171,7 +172,7 @@ typedef struct Tex {
struct PluginTex *plugin;
struct ColorBand *coba;
struct EnvMap *env;
-
+ struct PreviewImage * preview;
} Tex;
diff --git a/source/blender/makesdna/DNA_userdef_types.h b/source/blender/makesdna/DNA_userdef_types.h
index 2e83e773ce8..945fe5e00d3 100644
--- a/source/blender/makesdna/DNA_userdef_types.h
+++ b/source/blender/makesdna/DNA_userdef_types.h
@@ -205,6 +205,7 @@ extern UserDef U; /* from usiblender.c !!!! */
#define USER_NONUMPAD 8192
#define USER_LMOUSESELECT 16384
#define USER_FILECOMPRESS 32768
+#define USER_SAVE_PREVIEWS 65536
/* viewzom */
#define USER_ZOOM_CONT 0
diff --git a/source/blender/makesdna/DNA_world_types.h b/source/blender/makesdna/DNA_world_types.h
index 4b8dfe3812a..7349e37f3b7 100644
--- a/source/blender/makesdna/DNA_world_types.h
+++ b/source/blender/makesdna/DNA_world_types.h
@@ -108,6 +108,9 @@ typedef struct World {
struct Ipo *ipo;
struct MTex *mtex[10];
+ /* previews */
+ struct PreviewImage *preview;
+
ScriptLink scriptlink;
} World;
diff --git a/source/blender/python/api2_2x/Window.c b/source/blender/python/api2_2x/Window.c
index 22ae5586e2c..cf128ec8dd2 100644
--- a/source/blender/python/api2_2x/Window.c
+++ b/source/blender/python/api2_2x/Window.c
@@ -40,6 +40,7 @@
#include "BKE_scene.h" /* scene_find_camera() */
#include "BPI_script.h"
#include "BIF_mywindow.h"
+#include "BIF_imasel.h"
#include "BSE_headerbuttons.h"
#include "BSE_filesel.h"
#include "BIF_editmesh.h" /* for undo_push_mesh() */
diff --git a/source/blender/quicktime/apple/quicktime_import.c b/source/blender/quicktime/apple/quicktime_import.c
index c701d4d41d0..862b20b5260 100644
--- a/source/blender/quicktime/apple/quicktime_import.c
+++ b/source/blender/quicktime/apple/quicktime_import.c
@@ -244,6 +244,7 @@ static OSErr QT_get_frameIndexes(struct anim *anim)
TimeValue nextTime = 0;
TimeValue startPoint;
TimeValue tmpstartPoint;
+ long sampleCount = 0;
startPoint = -1;
@@ -254,12 +255,12 @@ static OSErr QT_get_frameIndexes(struct anim *anim)
anim->qtime->framecount = 0;
- while(tmpstartPoint != -1) {
- nextTime = 0;
- GetMovieNextInterestingTime(anim->qtime->movie, nextTimeMediaSample, 1, &media, tmpstartPoint, 0, &nextTime, NULL);
- tmpstartPoint = nextTime;
- anim->qtime->framecount ++;
- }
+ sampleCount = GetMediaSampleCount(anim->qtime->theMedia);
+ anErr = GetMoviesError();
+ if (anErr != noErr) return anErr;
+
+ anim->qtime->framecount = sampleCount;
+
anim->qtime->frameIndex = (TimeValue *) MEM_callocN(sizeof(TimeValue) * anim->qtime->framecount, "qtframeindex");
//rewind
@@ -403,6 +404,7 @@ int startquicktime (struct anim *anim)
char *qtname;
Str255 dst;
#endif
+ short depth = 0;
anim->qtime = MEM_callocN (sizeof(QuicktimeMovie),"animqt");
anim->qtime->have_gw = FALSE;
@@ -483,6 +485,9 @@ int startquicktime (struct anim *anim)
anim->qtime->offscreenGWorld,
GetGWorldDevice(anim->qtime->offscreenGWorld));
SetMoviePlayHints(anim->qtime->movie, hintsHighQuality, hintsHighQuality);
+
+ // sets Media and Track!
+ depth = GetFirstVideoTrackPixelDepth(anim);
QT_get_frameIndexes(anim);
}
@@ -491,7 +496,7 @@ int startquicktime (struct anim *anim)
LockPixels(anim->qtime->offscreenPixMap);
//fill blender's anim struct
- anim->qtime->depth = GetFirstVideoTrackPixelDepth(anim);
+ anim->qtime->depth = depth;
anim->duration = anim->qtime->framecount;
anim->params = 0;
diff --git a/source/blender/src/buttons_scene.c b/source/blender/src/buttons_scene.c
index 951a4ac25e4..ee5e194bd35 100644
--- a/source/blender/src/buttons_scene.c
+++ b/source/blender/src/buttons_scene.c
@@ -61,6 +61,7 @@
#include "BIF_graphics.h"
#include "BIF_glutil.h"
#include "BIF_interface.h"
+#include "BIF_imasel.h"
#include "BIF_keyval.h"
#include "BIF_mainqueue.h"
#include "BIF_mywindow.h"
diff --git a/source/blender/src/buttons_shading.c b/source/blender/src/buttons_shading.c
index 1e1a9b1e01f..ab0c1cb3ad2 100644
--- a/source/blender/src/buttons_shading.c
+++ b/source/blender/src/buttons_shading.c
@@ -94,6 +94,7 @@
#include "BIF_mywindow.h"
#include "BIF_space.h"
#include "BIF_glutil.h"
+#include "BIF_imasel.h"
#include "BIF_interface.h"
#include "BIF_toolbox.h"
#include "BIF_space.h"
@@ -876,7 +877,12 @@ static void image_load_fs_cb(void *ima_pp_v, void *iuser_v)
#else
else name = U.textudir;
#endif
- activate_fileselect_args(FILE_SPECIAL, "SELECT IMAGE", name, load_image_cb, ima_pp_v, iuser_v);
+ if (G.qual & LR_CTRLKEY) {
+ activate_imageselect_args(FILE_SPECIAL, "SELECT IMAGE", name, load_image_cb, ima_pp_v, iuser_v);
+ }
+ else {
+ activate_fileselect_args(FILE_SPECIAL, "SELECT IMAGE", name, load_image_cb, ima_pp_v, iuser_v);
+ }
}
/* 5 layer button callbacks... */
diff --git a/source/blender/src/drawimasel.c b/source/blender/src/drawimasel.c
index 45757170f78..00917233109 100644
--- a/source/blender/src/drawimasel.c
+++ b/source/blender/src/drawimasel.c
@@ -47,811 +47,613 @@
#endif
#include "MEM_guardedalloc.h"
-#include "BMF_Api.h"
-#include "BLI_blenlib.h"
-#include "IMB_imbuf_types.h"
+
+#include "DNA_ID.h"
#include "DNA_screen_types.h"
#include "DNA_space_types.h"
+#include "DNA_scene_types.h"
+#include "DNA_userdef_types.h"
+#include "DNA_object_types.h"
+#include "DNA_material_types.h"
+
+#include "BLI_blenlib.h"
+#ifdef WIN32
+#include "BLI_winstuff.h"
+#endif
+#include "BLI_storage_types.h"
+
#include "BKE_global.h"
+#include "BKE_library.h"
+#include "BKE_icons.h"
+#include "BKE_utildefines.h"
+#include "BIF_filelist.h"
-#include "BIF_fsmenu.h"
#include "BIF_gl.h"
-#include "BIF_resources.h"
+#include "BIF_glutil.h"
+#include "BIF_mywindow.h"
#include "BIF_screen.h"
+#include "BIF_resources.h"
+#include "BIF_language.h"
+
#include "BIF_interface.h"
#include "BIF_interface_icons.h"
-#include "BIF_imasel.h"
-#include "BIF_mywindow.h"
+#include "BIF_previewrender.h"
+#include "BIF_fsmenu.h"
#include "BIF_space.h"
-#include "BIF_resources.h"
+#include "BIF_gl.h"
+#include "BIF_glutil.h"
#include "BSE_drawimasel.h"
-#include "BSE_filesel.h"
+#include "BSE_drawipo.h" /* for v2d functions */
+#include "BSE_view.h"
-#include "blendef.h"
-#include "mydevice.h"
+#include "BLO_readfile.h"
-#define IMALINESIZE 16
-/* well, who would have thought ... */
-#define lrectwrite(a, b, c, d, rect) {glRasterPos2i(a, b);glDrawPixels((c)-(a)+1, (d)-(b)+1, GL_RGBA, GL_UNSIGNED_BYTE, rect);}
+#include "IMB_imbuf.h"
+#include "IMB_imbuf_types.h"
-/* GLOBALS */
-extern char *fsmenu;
+#include "PIL_time.h"
-void rectwrite_imasel(int , int , int , int , int , int , int , int , float , float , unsigned int *);
+#include "blendef.h"
+#include "mydevice.h"
-void rectwrite_imasel(int winxmin, int winymin, int winxmax, int winymax, int x1, int y1, int xim, int yim, float zoomx, float zoomy, unsigned int *rect)
-{
- int cx, cy, oldxim, x2, y2;
-
- oldxim= xim;
-
- /* coordinates how it will be put at screen */
- x2= x1+ zoomx*xim;
- y2= y1+ zoomy*yim;
-
- /* partial clip */
- if(x1<=winxmin) {
- /* with OpenGL, rects are not allowed to start outside of the left/bottom window edge */
- cx= winxmin-x1+(int)zoomx;
- /* make sure the rect will be drawn pixel-exact */
- cx/= zoomx;
- cx++;
- x1+= zoomx*cx;
- xim-= cx;
- rect+= cx;
- }
- if(y1<=winymin) {
- cy= winymin-y1+(int)zoomy;
- cy/= zoomy;
- cy++;
- y1+= zoomy*cy;
- rect+= cy*oldxim;
- yim-= cy;
+#include "interface.h" /* urm... for rasterpos_safe, roundbox */
+
+#define BUTTONWIDTH 20
+#define BOOKMARKWIDTH_MAX 240
+
+void calc_imasel_rcts(SpaceImaSel *simasel, int winx, int winy)
+{
+ int width = (int)16.0f*simasel->aspect;
+ int numtiles;
+ int numfiles = 0;
+ int tilewidth = simasel->prv_w + TILE_BORDER_X*4;
+ int tileheight = simasel->prv_h + TILE_BORDER_Y*4 + U.fontsize;
+
+ // complete area of the space
+ simasel->v2d.mask.xmin= simasel->v2d.mask.ymin = 0;
+ simasel->v2d.mask.xmax= winx;
+ simasel->v2d.mask.ymax= winy;
+
+ // vertical scroll bar
+ simasel->v2d.vert= simasel->v2d.mask;
+ simasel->v2d.vert.xmax -= TILE_BORDER_X + 2;
+ simasel->v2d.vert.xmin= simasel->v2d.vert.xmax- width - TILE_BORDER_X - 2;
+ simasel->v2d.vert.ymax -= IMASEL_BUTTONS_HEIGHT + TILE_BORDER_Y + 2;
+ simasel->v2d.vert.ymin += TILE_BORDER_Y + 2;
+ // simasel->v2d.mask.xmax= simasel->v2d.vert.xmin;
+
+ if (simasel->flag & FILE_BOOKMARKS) {
+ int bmwidth = (simasel->v2d.vert.xmin - simasel->v2d.mask.xmin)/4.0f;
+ if (bmwidth > BOOKMARKWIDTH_MAX) bmwidth = BOOKMARKWIDTH_MAX;
+
+ simasel->bookmarkrect.xmin = simasel->v2d.mask.xmin + TILE_BORDER_X;
+ simasel->bookmarkrect.xmax = simasel->v2d.mask.xmin + bmwidth - TILE_BORDER_X;
+ simasel->bookmarkrect.ymax = simasel->v2d.mask.ymax - IMASEL_BUTTONS_HEIGHT - TILE_BORDER_Y;
+ simasel->bookmarkrect.ymin = simasel->v2d.mask.ymin + TILE_BORDER_Y;
+
+ simasel->viewrect.xmin = simasel->bookmarkrect.xmax + TILE_BORDER_X;
+ simasel->viewrect.xmax = simasel->v2d.vert.xmin - TILE_BORDER_X;
+ simasel->viewrect.ymax = simasel->v2d.mask.ymax - IMASEL_BUTTONS_HEIGHT - TILE_BORDER_Y;
+ simasel->viewrect.ymin = simasel->v2d.mask.ymin + TILE_BORDER_Y;
+ } else {
+ simasel->viewrect.xmin = simasel->v2d.mask.xmin + TILE_BORDER_X;
+ simasel->viewrect.xmax = simasel->v2d.vert.xmin - TILE_BORDER_X;
+ simasel->viewrect.ymax = simasel->v2d.mask.ymax - IMASEL_BUTTONS_HEIGHT - TILE_BORDER_Y;
+ simasel->viewrect.ymin = simasel->v2d.mask.ymin + TILE_BORDER_Y;
}
- if(x2>=winxmax) {
- cx= x2-winxmax;
- cx/= zoomx;
- xim-= cx+3;
+
+ simasel->numtilesx = (simasel->viewrect.xmax - simasel->viewrect.xmin) / tilewidth;
+ simasel->numtilesy = (simasel->viewrect.ymax - simasel->viewrect.ymin) / tileheight;
+ numtiles = simasel->numtilesx*simasel->numtilesy;
+
+ if (simasel->files) {
+ numfiles = BIF_filelist_numfiles(simasel->files);
}
- if(y2>=winymax) {
- cy= y2-winymax;
- cy/= zoomy;
- yim-= cy+3;
+ if (numtiles > numfiles) numtiles = numfiles;
+
+ simasel->scrollarea = ((float)simasel->v2d.vert.ymax - (float)simasel->v2d.vert.ymin);
+ if (numtiles < numfiles) {
+ simasel->scrollheight = ((float)numtiles / (float)numfiles)*simasel->scrollarea;
+ simasel->scrollarea -= simasel->scrollheight;
+ } else {
+ simasel->scrollheight = simasel->scrollarea;
}
-
- if(xim<=0) return;
- if(yim<=0) return;
+ if (simasel->scrollarea < 0) simasel->scrollarea = 0;
+}
-// mywinset(curarea->win);
- glScissor(winxmin, winymin, winxmax-winxmin+1, winymax-winymin+1);
-
- glPixelStorei(GL_UNPACK_ROW_LENGTH, oldxim);
-
- glPixelZoom(zoomx, zoomy);
+void draw_imasel_scroll(SpaceImaSel *simasel)
+{
+ rcti scrollbar;
+ rcti scrollhandle;
- glRasterPos2i(x1, y1);
- glDrawPixels(xim, yim, GL_RGBA, GL_UNSIGNED_BYTE, rect);
+ scrollbar.xmin= simasel->v2d.cur.xmin + simasel->v2d.vert.xmin;
+ scrollbar.ymin = simasel->v2d.cur.ymin + simasel->v2d.vert.ymin;
+ scrollbar.xmax= simasel->v2d.cur.xmin + simasel->v2d.vert.xmax;
+ scrollbar.ymax = simasel->v2d.cur.ymin + simasel->v2d.vert.ymax;
- glPixelZoom(1.0, 1.0);
+ scrollhandle.xmin= scrollbar.xmin;
+ scrollhandle.ymin = scrollbar.ymax - simasel->scrollpos -1;
+ scrollhandle.xmax= scrollbar.xmax-1;
+ scrollhandle.ymax = scrollbar.ymax - simasel->scrollpos - simasel->scrollheight;
- glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
-}
+ BIF_ThemeColor(TH_SHADE1);
+ glRecti(scrollbar.xmin, scrollbar.ymin, scrollbar.xmax, scrollbar.ymax);
+ uiEmboss(scrollbar.xmin-2, scrollbar.ymin-2, scrollbar.xmax+2, scrollbar.ymax+2, 1);
-void viewgate(short sx, short sy, short ex, short ey)
-{
- short wx, wy;
- wx = curarea->winrct.xmin; wy = curarea->winrct.ymin;
- glViewport(wx+sx, wy+sy, (wx+ex )-(wx+sx)+1, (wy+ey )-(wy+sy)+1);
- glScissor(wx+sx, wy+sy, (wx+ex )-(wx+sx)+1, (wy+ey )-(wy+sy)+1);
- myortho2((float)sx-0.375 , (float)ex-0.375, (float)sy-0.375, (float)ey-0.375);
-}
+ BIF_ThemeColor(TH_SHADE2);
+ glRecti(scrollhandle.xmin, scrollhandle.ymin, scrollhandle.xmax, scrollhandle.ymax);
-void areaview (void)
-{
- short wx, wy;
- wx = curarea->winrct.xmin; wy = curarea->winrct.ymin;
- glViewport(wx, wy, curarea->winx, curarea->winy);
- glScissor(wx, wy, curarea->winx, curarea->winy);
- myortho2(-0.375, (float)(curarea->winx)-0.375, -0.375, (float)(curarea->winy)-0.375);
-
+ uiEmboss(scrollhandle.xmin, scrollhandle.ymin, scrollhandle.xmax, scrollhandle.ymax, 1);
}
-
-void calc_hilite(SpaceImaSel *simasel)
+
+static void draw_tile(SpaceImaSel *simasel, short sx, short sy, int colorid)
{
- OneSelectableIma *ima;
- ImaDir *direntry;
- short mx, my;
- int i, area_event;
-
- if (simasel->hilite > -1) {
- direntry = simasel->firstdir;
- while(direntry){
- direntry->hilite = 0;
- direntry = direntry->next;
- }
- simasel->hilite = -1;
- }
-
- if (simasel->totalima){
- simasel->hilite_ima = 0;
- ima = simasel->first_sel_ima;
- while (ima){
- ima->selectable = 0;
- ima = ima->next;
- }
- }
-
- area_event = 0;
- mx = simasel->mx;
- my = simasel->my;
-
- if (simasel->desx > 0){
- if ( (mx > simasel->desx) && (mx < simasel->deex) && (my > simasel->desy) && (my < simasel->deey) ) area_event = IMS_INDIR;
- }
- if (simasel->fesx > 0){
- if ( (mx > simasel->fesx) && (mx < simasel->feex) && (my > simasel->fesy) && (my < simasel->feey) ) area_event = IMS_INFILE;
- }
-
- switch(area_event){
- case IMS_INDIR:
- simasel->hilite = simasel->topdir + ((simasel->deey - my - 4) / IMALINESIZE);
-
- if (my >= simasel->deey) simasel->hilite = -1;
- if (simasel->hilite >= simasel->totaldirs) simasel->hilite = -1;
-
- if (simasel->hilite > -1){
- direntry = simasel->firstdir;
- for (i = simasel->hilite; i>0; i--){
- direntry = direntry->next;
- }
- direntry->hilite = 1;
-
- }
- simasel->mouse_move_redraw = 1;
- break;
-
- case IMS_INFILE:
- if (simasel->totalima){
- ima = simasel->first_sel_ima;
- while (ima){
- ima->selectable = 0;
-
- if (ima->draw_me) {
- if ((mx > ima->sx) && (mx < ima->sx+76) && (my > ima->sy-16) && (my < ima->sy+76)) {
- ima->selectable = 1;
- simasel->hilite_ima = ima;
- simasel->mouse_move_redraw = 1;
- }
- }
-
- ima = ima->next;
- }
- }
- break;
- }
+ /* TODO: BIF_ThemeColor seems to need this to show the color, not sure why? - elubie */
+ glEnable(GL_BLEND);
+ glColor4ub(0, 0, 0, 100);
+ glDisable(GL_BLEND);
+
+ BIF_ThemeColor4(colorid);
+ uiSetRoundBox(15);
+ uiRoundBox(sx+TILE_BORDER_X, sy - simasel->prv_h - TILE_BORDER_Y*3 - U.fontsize, sx + simasel->prv_w + TILE_BORDER_X*3, sy, 6);
}
-
-void make_sima_area(SpaceImaSel *simasel)
-{
- OneSelectableIma *ima;
- short rh, dm, sc;
- short boxperline, boxlines, boxlinesinview, boxlinesleft;
-
-/* ima slider box */
- simasel->fssx = 8;
- simasel->fssy = 8;
- simasel->fsex = 30;
- simasel->fsey = curarea->winy-64;
-/* ima entry's box */
- simasel->fesx = simasel->fsex + 8;
- simasel->fesy = simasel->fssy;
- simasel->feex = curarea->winx- 8;
- simasel->feey = curarea->winy-64;
-/* ima names */
- simasel->dnsx = 38;
- simasel->dnsy = curarea->winy - 29;
- simasel->dnw = curarea->winx - 8 - 38;
- simasel->dnh = 21;
- simasel->fnsx = simasel->fesx;
- simasel->fnsy = curarea->winy - 29 - 29;
- simasel->fnw = curarea->winx - 8 - simasel->fnsx;
- simasel->fnh = 21;
-
- if ((simasel->mode & 1)==1){
- /* dir slider box */
- simasel->dssx = 8;
-
- simasel->dsex = 30;
- simasel->dsey = curarea->winy-64;
- /* dir entry's box */
- simasel->desx = 38;
- simasel->desy = 8;
-
- simasel->deex = 208;
- simasel->deey = curarea->winy-64;
- simasel->dssy = simasel->desy;
- if (simasel->deex > (curarea->winx -8) ) simasel->deex = curarea->winx - 8;
- if (simasel->deex <= simasel->desx ) simasel->dssx = 0;
- /* file slider & entry & name box ++ */
- simasel->fssx += 216;
- simasel->fsex += 216;
- simasel->fesx += 216;
- simasel->fnsx += 216;
- simasel->fnw -= 216;
- }else{
- simasel->desx = 0;
- }
-
- if ((simasel->mode & 2) == 2){
- simasel->fesy += 32;
- simasel->infsx = simasel->fesx; simasel->infsy = 8;
- simasel->infex = simasel->feex; simasel->infey = 28;
- }else{
- simasel->infsx = 0;
+static float shorten_string(SpaceImaSel *simasel, char* string, float w)
+{
+ short shortened = 0;
+ float sw = 0;
+
+ sw = BIF_GetStringWidth(simasel->curfont, string, 0);
+ while (sw>w) {
+ int slen = strlen(string);
+ string[slen-1] = '\0';
+ sw = BIF_GetStringWidth(simasel->curfont, string, 0);
+ shortened = 1;
}
-
- simasel->dsdh = simasel->deey - simasel->desy - 4;
-
- if (simasel->dsdh <= 16) { simasel->desx = 0; }
- if ((simasel->feex-16) <= simasel->fesx) { simasel->fesx = 0; }
- if ((simasel->infex-16) <= simasel->infsx) { simasel->infsx = 0; }
-
- if ((simasel->deey ) <= simasel->desy) { simasel->desx = 0; }
- if ((simasel->feey ) <= simasel->fesy) { simasel->fesx = 0; }
- if ((simasel->infey ) > simasel->feey) { simasel->infsx = 0;}
-
- /* Dir Slider */
- if (simasel->desx != 0){
- simasel->dirsli = 0;
-
- simasel->dirsli_lines = (simasel->dsdh / IMALINESIZE);
- simasel->dirsli_h = 0;
-
- if (simasel->topdir < 0) simasel->topdir = 0;
- if (simasel->topdir > (simasel->totaldirs - simasel->dirsli_lines) ) simasel->topdir = (simasel->totaldirs - simasel->dirsli_lines);
-
- if ( (simasel->totaldirs * IMALINESIZE) >= simasel->dsdh ){
- simasel->dirsli = 1;
- simasel->dirsli_sx = simasel->dssx+2;
- simasel->dirsli_ex = simasel->dsex-2;
-
- simasel->dirsli_h = (simasel->dsdh) * (float)simasel->dirsli_lines / (float)simasel->totaldirs;
- simasel->dirsli_ey = simasel->dsey - 2;
- if (simasel->topdir) {
- rh = (simasel->dsdh - simasel->dirsli_h);
- simasel->dirsli_ey -= rh * (float)((float)simasel->topdir / (float)(simasel->totaldirs - simasel->dirsli_lines ));
- }
-
- if (simasel->dirsli_h < 4) simasel->dirsli_h = 4;
-
- }else{
- simasel->topdir = 0;
- }
- }
-
- if (simasel->totalima){
- /* there are images */
-
- ima = simasel->first_sel_ima;
-
-
- boxperline = (simasel->feex - simasel->fesx) / 80;
- if (boxperline) boxlines = 1 + (simasel->totalima / boxperline); else boxlines = 1;
- boxlinesinview = (simasel->feey - simasel->fesy) / 100;
- boxlinesleft = boxlines - boxlinesinview;
-
- if (boxlinesleft > 0){
- /* slider needed */
-
- simasel->slider_height = boxlinesinview / (float)(boxlines+1);
- simasel->slider_space = 1.0 - simasel->slider_height;
-
- simasel->imasli_sx = simasel->fssx+1;
- simasel->imasli_ex = simasel->fsex-1;
- simasel->fsdh = simasel->fsey - simasel->fssy - 4;
-
- simasel->imasli_h = simasel->fsdh * simasel->slider_height;
- if (simasel->imasli_h < 6) simasel->imasli_h = 6;
- simasel->imasli_ey = simasel->fsey - 2 - (simasel->fsdh * simasel->slider_space * simasel->image_slider);
-
- simasel->imasli = 1;
-
- }else{
- simasel->image_slider = 0;
- simasel->imasli = 0;
- }
-
- sc = simasel->image_slider * (boxlinesleft * 100);
-
- simasel->curimax = simasel->fesx + 8;
- simasel->curimay = simasel->feey - 90 + sc;
-
- dm = 1;
- if (simasel->curimay-2 < simasel->fesy) dm = 0;
- // let first row of icons remain selectable
- if(OLD_IMASEL) if (simasel->curimay+80 > simasel->feey) dm = 0;
- if (simasel->curimax+72 > simasel->feex) dm = 0;
-
- simasel->total_selected = 0;
- while (ima){
- ima->draw_me = dm;
-
- if (ima->selected) simasel->total_selected++;
-
- ima->sx = simasel->curimax;
- ima->sy = simasel->curimay+16;
-
- ima->ex = ima->sx + ima->dw;
- ima->ey = ima->sy + ima->dh;
-
- simasel->curimax += 80;
- if (simasel->curimax + 72 > simasel->feex){
-
- simasel->curimax = simasel->fesx + 8;
- simasel->curimay -= 100;
-
- dm = 1;
- // let icons that fall off (top/bottom) be selectable
- if(OLD_IMASEL) {
- if (simasel->curimay+80 > simasel->feey) dm = 0;
- if (simasel->curimay-8 < simasel->fesy) dm = 0;
- }
-
- }
- ima = ima->next;
+ if (shortened) {
+ int slen = strlen(string);
+ if (slen > 3) {
+ BLI_strncpy(string+slen-3, "...", 4);
}
}
+ return sw;
}
-static void str_image_type(int ftype, char *name)
+static void draw_file(SpaceImaSel *simasel, short sx, short sy, struct direntry *file)
{
- strcpy(name, "");
-
- if((ftype & JPG_MSK) == JPG_STD) strcat(name, "std ");
- if((ftype & JPG_MSK) == JPG_VID) strcat(name, "video ");
- if((ftype & JPG_MSK) == JPG_JST) strcat(name, "amiga ");
- if((ftype & JPG_MSK) == JPG_MAX) strcat(name, "max ");
-
- if( ftype == AN_hamx) { strcat(name, "hamx "); return; }
+ short soffs;
+ char fname[FILE_MAXFILE];
+ float sw;
+
+ BLI_strncpy(fname,file->relname, FILE_MAXFILE);
+ sw = shorten_string(simasel, fname, simasel->prv_w );
+ soffs = (simasel->prv_w + TILE_BORDER_X*4 - sw) / 2;
- if( ftype == IMAGIC ) { strcat(name, "sgi "); return; }
- if( ftype & JPG ) { strcat(name, "jpeg "); }
- if( ftype & TGA ) { strcat(name, "targa "); }
- if( ftype & PNG ) { strcat(name, "png "); }
- if( ftype & BMP ) { strcat(name, "bmp "); }
- if( ftype & AMI ) { strcat(name, "iff "); }
-#ifdef WITH_QUICKTIME
- if( ftype & QUICKTIME ) { strcat(name, "quicktime "); }
+ ui_rasterpos_safe(sx+soffs, sy - simasel->prv_h - TILE_BORDER_Y*2 - U.fontsize, simasel->aspect);
+#ifdef WIN32
+ BIF_DrawString(simasel->curfont, fname, ((U.transopts & USER_TR_MENUS) | CONVERT_TO_UTF8));
+#else
+ BIF_DrawString(simasel->curfont, fname, (U.transopts & USER_TR_MENUS));
#endif
}
-void draw_sima_area(SpaceImaSel *simasel)
-{
- uiBlock *block;
- OneSelectableIma *ima;
- ImaDir *direntry;
- float col[3];
- int i, info;
- short sx, sy, ex, ey, sc;
- char naam[256], infostr[256];
-
- BIF_GetThemeColor3fv(TH_BACK, col);
- glClearColor(col[0], col[1], col[2], 0.0);
- glClear(GL_COLOR_BUFFER_BIT);
-
- sprintf(naam, "win %d", curarea->win);
- block= uiNewBlock(&curarea->uiblocks, naam, UI_EMBOSS, UI_HELV, curarea->win);
- uiBlockSetCol(block, TH_BUT_SETTING1);
-
- if (simasel->desx > 0){
- /* DIR ENTRYS */
- BIF_ThemeColorShade(TH_SHADE1, -70);
- glRecti(simasel->dssx, simasel->dssy, simasel->dsex, simasel->dsey);
- glRecti(simasel->desx, simasel->desy, simasel->deex, simasel->deey);
-
- uiEmboss(simasel->dssx, simasel->dssy, simasel->dsex, simasel->dsey,1);
- uiEmboss(simasel->desx, simasel->desy, simasel->deex, simasel->deey,1);
+static void draw_imasel_bookmarks(ScrArea *sa, SpaceImaSel *simasel)
+{
+ char bookmark[FILE_MAX];
+ float sw;
+
+ if (simasel->flag & FILE_BOOKMARKS) {
+ int nentries = fsmenu_get_nentries();
+ int i;
+ short sx, sy;
+ int bmwidth;
+ int linestep = U.fontsize*3/2;
- if (simasel->dirsli == 1) {
- sx = simasel->dirsli_sx+2;
- sy = simasel->dirsli_ey - simasel->dirsli_h+2;
- ex = simasel->dirsli_ex-2;
- ey = simasel->dirsli_ey-2;
+ sx = simasel->bookmarkrect.xmin + TILE_BORDER_X;
+ sy = simasel->bookmarkrect.ymax - TILE_BORDER_Y - linestep;
+ bmwidth = simasel->bookmarkrect.xmax - simasel->bookmarkrect.xmin - 2*TILE_BORDER_X;
+
+ if (bmwidth < 0) return;
+
+ for (i=0; i< nentries && sy > linestep ;++i) {
+ char *fname = fsmenu_get_entry(i);
+ char *sname = NULL;
- BIF_ThemeColor(TH_SHADE1);
+ if (fname) {
+ int sl;
+ BLI_strncpy(bookmark, fname, FILE_MAX);
- glRecti(sx, sy, ex, ey);
- uiEmboss(sx, sy, ex,ey,0);
- }
- if (simasel->totaldirs) {
- sx = simasel->desx+8;
- sy = simasel->deey-IMALINESIZE;
-
- direntry = simasel->firstdir;
- if (simasel->topdir){
- for(i = simasel->topdir; i>0; i--){
- direntry = direntry->next;
+ sl = strlen(bookmark)-1;
+ if (bookmark[sl] == '\\' || bookmark[sl] == '/') {
+ bookmark[sl] = '\0';
+ sl--;
}
- }
- viewgate(simasel->desx, simasel->desy, simasel->deex-4, simasel->deey);
-
- i = simasel->dirsli_lines;
- if (i > simasel->totaldirs) i = simasel->totaldirs;
- for(;i > 0; i--){
- strcpy(naam, direntry->name);
-
- cpack(0xFFFFFF);
- if (direntry->selected == 1){
- cpack(0x7777CC);
- glRecti(simasel->desx+2, sy-4, simasel->deex-4, sy+IMALINESIZE-4);
- cpack(0xFFFFFF);
+ while (sl) {
+ if (bookmark[sl] == '\\' || bookmark[sl] == '/'){
+ sl++;
+ break;
+ };
+ sl--;
}
- if (direntry->hilite == 1){
- cpack(0x999999);
- glRecti(simasel->desx+2, sy-4, simasel->deex-4, sy+IMALINESIZE-4);
- cpack(0xFFFFFF);
+ sname = &bookmark[sl];
+ sw = shorten_string(simasel, sname, bmwidth);
+ if (simasel->active_bookmark == i ) {
+ BIF_ThemeColor(TH_TEXT_HI);
+ } else {
+ BIF_ThemeColor(TH_TEXT);
}
-
- glRasterPos2i(sx, sy);
- BMF_DrawString(G.font, naam);
-
- direntry = direntry->next;
- sy-=IMALINESIZE;
+ ui_rasterpos_safe(sx, sy, simasel->aspect);
+#ifdef WIN32
+ BIF_DrawString(simasel->curfont, sname, ((U.transopts & USER_TR_MENUS) | CONVERT_TO_UTF8));
+#else
+ BIF_DrawString(simasel->curfont, sname, (U.transopts & USER_TR_MENUS));
+#endif
+ sy -= linestep;
+ } else {
+ cpack(0xB0B0B0);
+ sdrawline(sx, sy + U.fontsize/2 , sx + bmwidth, sy + U.fontsize/2);
+ cpack(0x303030);
+ sdrawline(sx, sy + 1 + U.fontsize/2 , sx + bmwidth, sy + 1 + U.fontsize/2);
+ sy -= linestep;
}
- areaview();
-
- }
-
- /* status icons */
-
- sx = simasel->desx;
- sy = simasel->deey+6;
-
- if (bitset(simasel->fase, IMS_FOUND_BIP)) {
- BIF_icon_draw(sx+16*0, sy, ICON_BPIBFOLDER_HLT);
- } else if (bitset(simasel->fase, IMS_WRITE_NO_BIP)) {
- BIF_icon_draw(sx+16*0, sy, ICON_BPIBFOLDER_DEHLT);
- } else {
- BIF_icon_draw(sx+16*0, sy, ICON_BPIBFOLDER_DEHLT);
}
- if (bitset(simasel->fase, IMS_KNOW_INF)) {
- BIF_icon_draw(sx+16*1, sy, ICON_FOLDER_HLT);
+ uiEmboss(simasel->bookmarkrect.xmin, simasel->bookmarkrect.ymin, simasel->bookmarkrect.xmax-1, simasel->bookmarkrect.ymax-1, 1);
+ }
+}
+
+static void draw_imasel_previews(ScrArea *sa, SpaceImaSel *simasel)
+{
+ static double lasttime= 0;
+ struct FileList* files = simasel->files;
+ int numfiles;
+ struct direntry *file;
+ int numtiles;
+
+ int tilewidth = simasel->prv_w + TILE_BORDER_X*4;
+ int tileheight = simasel->prv_h + TILE_BORDER_Y*4 + U.fontsize;
+ short sx, sy;
+ int do_load = 1;
+
+ ImBuf* imb=0;
+ int i,j;
+ short type;
+ int colorid = 0;
+ int todo;
+ int fileoffset, rowoffset, columnoffset;
+ float scrollofs;
+
+
+ rcti viewrect = simasel->viewrect;
+
+ if (!files) return;
+ /* Reload directory */
+ BLI_strncpy(simasel->dir, BIF_filelist_dir(files), FILE_MAXDIR);
+
+ type = BIF_filelist_gettype(simasel->files);
+
+ if (BIF_filelist_empty(files))
+ {
+ unsigned int filter = 0;
+ BIF_filelist_hidedot(simasel->files, simasel->flag & FILE_HIDE_DOT);
+ if (simasel->flag & FILE_FILTER) {
+ filter = simasel->filter ;
} else {
- BIF_icon_draw(sx+16*1, sy, ICON_FOLDER_DEHLT);
+ filter = 0;
}
+
+ BIF_filelist_setfilter(simasel->files, filter);
+ BIF_filelist_readdir(files);
- if (bitset(simasel->fase, IMS_KNOW_IMA)) {
- BIF_icon_draw(sx+16*2, sy, ICON_BLUEIMAGE_HLT);
- } else {
- BIF_icon_draw(sx+16*2, sy, ICON_BLUEIMAGE_DEHLT);
- }
+ if(simasel->sort!=FILE_SORTALPHA) BIF_filelist_sort(simasel->files, simasel->sort);
}
-
- if (simasel->fesx > 0) {
- int extrabutsize;
-
- BIF_ThemeColorShade(TH_SHADE1, -80);
- glRecti(simasel->fssx, simasel->fssy, simasel->fsex, simasel->fsey);
+ BIF_filelist_imgsize(simasel->files,simasel->prv_w,simasel->prv_h);
- glRecti(simasel->fesx, simasel->fesy, simasel->feex, simasel->feey);
+ numfiles = BIF_filelist_numfiles(files);
+ numtiles = simasel->numtilesx*simasel->numtilesy;
- uiEmboss(simasel->fssx-1, simasel->fssy-1, simasel->fsex+1, simasel->fsey+1,1);
- uiEmboss(simasel->fesx-1, simasel->fesy-1, simasel->feex+1, simasel->feey+1,1);
-
- if (simasel->imasli == 1){
- sx = simasel->imasli_sx;
- sy = simasel->imasli_ey - simasel->imasli_h;
- ex = simasel->imasli_ex;
- ey = simasel->imasli_ey;
-
- BIF_ThemeColor(TH_SHADE1);
+ if (numtiles > numfiles) numtiles = numfiles;
+
+ todo = 0;
+ if (lasttime < 0.001) lasttime = PIL_check_seconds_timer();
- glRecti(sx, sy, ex, ey);
- uiEmboss(sx, sy, ex, ey, 1);
- }
- info = 0;
- strcpy(infostr, "");
- if (simasel->totalima){
- viewgate(simasel->fesx, simasel->fesy, simasel->feex, simasel->feey);
-
- ima = simasel->first_sel_ima;
-
- while (ima){
- sc = 0;
-
- sx = ima->sx- 6; sy = ima->sy-20 + sc;
- ex = ima->sx+71; ey = ima->sy+70 + sc;
-
- if(ima->selected == 1){
- cpack(0xCC6666);
- glRecti(sx, sy, ex, ey);
- }
- if(ima->selectable == 1){
- if (ima->selected ) cpack(0xEE8888); else cpack(0x999999);
-
- if (((simasel->mode & 8) != 8) && (simasel->hilite_ima == ima)){
- glRecti(sx, sy, ex, ey); uiEmboss(sx,sy, ex,ey, 1);
- }
- if (ima->disksize/1000 > 1000){ sprintf(infostr, "%s %.2fMb x%i y%i %i bits ",ima->file_name,(ima->disksize/1024)/1024.0, ima->orgx, ima->orgy, ima->orgd);
- }else{ sprintf(infostr, "%s %dKb %ix%i %i bits ", ima->file_name,ima->disksize/1024, ima->orgx, ima->orgy, ima->orgd);
- }
- if (ima->anim == 1){ strcat (infostr, "movie"); }else{
- str_image_type(ima->ibuf_type, naam);
- strcat (infostr, naam);
- }
- info = 1;
+ if (simasel->numtilesx > 0) {
+ /* calculate the offset to start drawing */
+ if ((numtiles < numfiles) && (simasel->scrollarea > 0)) {
+ fileoffset = numfiles*( (simasel->scrollpos) / simasel->scrollarea) + 0.5;
+ } else {
+ fileoffset = 0;
+ }
+ rowoffset = (fileoffset / simasel->numtilesx)*simasel->numtilesx;
+ columnoffset = fileoffset % simasel->numtilesx;
+ scrollofs = (float)tileheight*(float)columnoffset/(float)simasel->numtilesx;
+ } else {
+ rowoffset = 0;
+ scrollofs = 0;
+ }
+ /* add partially visible row */
+ numtiles += simasel->numtilesx;
+ for (i=rowoffset, j=0 ; (i < numfiles) && (j < numtiles); ++i, ++j)
+ {
+ sx = simasel->v2d.cur.xmin + viewrect.xmin + (j % simasel->numtilesx)*tilewidth;
+ sy = simasel->v2d.cur.ymin + viewrect.ymax + (short)scrollofs - (viewrect.ymin + (j / simasel->numtilesx)*tileheight);
+
+ file = BIF_filelist_file(files, i);
+
+ if (simasel->active_file == i) {
+ colorid = TH_ACTIVE;
+ draw_tile(simasel, sx, sy, colorid);
+ } else if (file->flags & ACTIVE) {
+ colorid = TH_HILITE;
+ draw_tile(simasel, sx, sy, colorid);
+ } else {
+ /*
+ colorid = TH_PANEL;
+ draw_tile(simasel, sx, sy, colorid);
+ */
+ }
+
+ if ( type == FILE_MAIN) {
+ ID *id;
+ int icon_id = 0;
+ int idcode;
+ idcode= BIF_groupname_to_code(simasel->dir);
+ if (idcode == ID_MA || idcode == ID_TE || idcode == ID_LA || idcode == ID_WO || idcode == ID_IM) {
+ id = (ID *)file->poin;
+ icon_id = BKE_icon_getid(id);
+ }
+ if (icon_id) {
+ glEnable(GL_BLEND);
+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+ if (do_load) {
+ BIF_icon_draw_preview(sx+2*TILE_BORDER_X, sy-simasel->prv_w-TILE_BORDER_X, icon_id, 0);
+ } else {
+ BIF_icon_draw_preview(sx+2*TILE_BORDER_X, sy-simasel->prv_w-TILE_BORDER_X, icon_id, 1);
+ todo++;
}
- sx = ima->sx; sy = ima->sy + sc;
- ex = ima->ex; ey = ima->ey + sc;
-
- if (ima->anim == 0) BIF_ThemeColorShade(TH_SHADE1, -80);
- else BIF_ThemeColorShade(TH_SHADE1, -70);
-
- glRecti(sx, sy, ex, ey);
- uiEmboss(sx-1,sy-1, ex+1,ey+1, 1);
-
- cpack(0);
- strcpy(naam, ima->file_name);
- naam[11] = 0;
-
- glRasterPos2i(sx+32-BMF_GetStringWidth(G.fonts, naam) / 2 , sy-16);
- BMF_DrawString(G.fonts, naam);
-
- if ((ima) && (ima->pict) && (ima->pict->rect)){
- if ( (ey > simasel->fesy) && (sy < simasel->feey)){
- if(OLD_IMASEL) {
- lrectwrite(sx, sy, ex-1, ey-1, ima->pict->rect);
- } else
- rectwrite_imasel(simasel->fesx, simasel->fesy,
- curarea->winrct.xmax, curarea->winrct.ymax - 64, //simasel->feey*1.5,
- sx, sy, ima->pict->x, ima->pict->y, 1.0, 1.0, ima->pict->rect);
- }
+ glDisable(GL_BLEND);
+ }
+ }
+ else {
+ if ( (file->flags & IMAGEFILE) || (file->flags & MOVIEFILE))
+ {
+ if (do_load) {
+ BIF_filelist_loadimage(simasel->files, i);
+ } else {
+ todo++;
}
-
- ima = ima->next;
+ imb = BIF_filelist_getimage(simasel->files, i);
+ } else {
+ imb = BIF_filelist_getimage(simasel->files, i);
}
-
- if ((simasel->mode & 8) == 8) { /* if magnify */
-
- if (bitset(simasel->fase, IMS_KNOW_IMA) && (simasel->hilite_ima)) {
-
- ima = simasel->hilite_ima;
- glPixelZoom(2.0, 2.0);
-
- sx = ima->sx + (ima->ex - ima->sx)/2 - (ima->ex - ima->sx);
- sy = ima->sy + (ima->ey - ima->sy)/2 - (ima->ey - ima->sy);
-
- ex = sx + 2*(ima->ex - ima->sx);
- ey = sy + 2*(ima->ey - ima->sy);
-
- uiEmboss(sx-1,sy-1, ex+1,ey+1, 0);
-
- if(OLD_IMASEL) {
- lrectwrite(sx, sy, sx+ (ima->ex - ima->sx)-1, sy+ (ima->ey - ima->sy)-1, ima->pict->rect);
- } else
- rectwrite_imasel(simasel->fesx, simasel->fesy,
- curarea->winrct.xmax, curarea->winrct.ymax - 64, //simasel->feey*1.5,
- sx, sy, ima->pict->x, ima->pict->y, 2.0, 2.0, ima->pict->rect);
+
+ if (imb) {
+ float fx = ((float)simasel->prv_w - (float)imb->x)/2.0f;
+ float fy = ((float)simasel->prv_h - (float)imb->y)/2.0f;
+ short dx = (short)(fx + 0.5f);
+ short dy = (short)(fy + 0.5f);
- glPixelZoom(1.0, 1.0);
+ glEnable(GL_BLEND);
+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+ // glaDrawPixelsSafe((float)sx+8 + dx, (float)sy - imgwidth + dy - 8, imb->x, imb->y, imb->x, GL_RGBA, GL_UNSIGNED_BYTE, imb->rect);
+ glColor4f(1.0, 1.0, 1.0, 1.0);
+ glaDrawPixelsTex((float)sx+2*TILE_BORDER_X + dx, (float)sy - simasel->prv_h + dy - 2*TILE_BORDER_Y, imb->x, imb->y,GL_UNSIGNED_BYTE, imb->rect);
+ // glDisable(GL_BLEND);
+ imb = 0;
+ }
+ }
+
+ if (type == FILE_MAIN) {
+ glColor3f(1.0f, 1.0f, 1.0f);
+ }
+ else {
+ if (S_ISDIR(file->type)) {
+ glColor3f(1.0f, 1.0f, 0.9f);
+ }
+ else if (file->flags & IMAGEFILE) {
+ BIF_ThemeColor(TH_SEQ_IMAGE);
+ }
+ else if (file->flags & MOVIEFILE) {
+ BIF_ThemeColor(TH_SEQ_MOVIE);
+ }
+ else if (file->flags & BLENDERFILE) {
+ BIF_ThemeColor(TH_SEQ_SCENE);
+ }
+ else {
+ if (simasel->active_file == i) {
+ BIF_ThemeColor(TH_GRID); /* grid used for active text */
+ } else if (file->flags & ACTIVE) {
+ BIF_ThemeColor(TH_TEXT_HI);
+ } else {
+ BIF_ThemeColor(TH_TEXT);
}
}
- areaview(); /* reset viewgate */
}
-
-
- /* INFO */
- if (simasel->infsx > 0){
- BIF_ThemeColorShade(TH_SHADE1, -80);
-
- glRecti(simasel->infsx, simasel->infsy, simasel->infex, simasel->infey);
- uiEmboss(simasel->infsx, simasel->infsy, simasel->infex, simasel->infey,1);
-
- if ((info)&&(strlen(infostr) > 0)){
-
- sx = curarea->winrct.xmin;
- sy = curarea->winrct.ymin;
-
- viewgate(simasel->infsx, simasel->infsy, simasel->infex, simasel->infey);
- cpack(0xAAAAAA);
- glRasterPos2i(simasel->infsx+4, simasel->infsy+6);
- BMF_DrawString(G.font, infostr);
-
- areaview(); /* reset viewgate */
-
- }
- }
-
- extrabutsize= (simasel->returnfunc)?60:0;
- if (simasel->dnw > extrabutsize+8) {
- simasel->dnw-= extrabutsize;
- uiDefBut(block, TEX, 1,"", simasel->dnsx, simasel->dnsy, simasel->dnw, simasel->dnh, simasel->dir, 0.0, (float)FILE_MAXFILE-1, 0, 0, "");
- if (extrabutsize)
- uiDefBut(block, BUT, 5, "Load", simasel->dnsx+simasel->dnw, simasel->dnsy, extrabutsize, 21, NULL, 0.0, 0.0, 0, 0, "Load the selected image");
- }
- if (simasel->fnw > extrabutsize+8) {
- simasel->fnw-= extrabutsize;
- uiDefBut(block, TEX, 2,"", simasel->fnsx, simasel->fnsy, simasel->fnw, simasel->fnh, simasel->file, 0.0, (float)FILE_MAXFILE-1, 0, 0, "");
- if (extrabutsize)
- uiDefBut(block, BUT, 6, "Cancel", simasel->fnsx+simasel->fnw, simasel->fnsy, extrabutsize, 21, NULL, 0.0, 0.0, 0, 0, "Cancel image loading");
+ draw_file(simasel, sx, sy, file);
+
+ if(do_load && (PIL_check_seconds_timer() - lasttime > 0.3)) {
+ lasttime= PIL_check_seconds_timer();
+ do_load = 0;
}
}
-
- if (curarea->winx > 16) {
- char *menu= fsmenu_build_menu();
-
- uiDefBut(block, BUT, 13, "P", 8, (short)(curarea->winy-29), 20, 21, 0, 0, 0, 0, 0, "");
- uiDefButS(block, MENU, 3 , menu, 8, (short)(curarea->winy-58), 20, 21, &simasel->fileselmenuitem, 0, 0, 0, 0, "");
- MEM_freeN(menu);
- }
-
- uiDrawBlock(block);
+ if (!do_load && todo > 0) /* we broke off loading */
+ addafterqueue(sa->win, RENDERPREVIEW, 1);
}
-void select_ima_files(SpaceImaSel *simasel)
+
+/* in panel space! */
+static void imasel_imgdraw(ScrArea *sa, uiBlock *block)
{
- short set_reset;
- short mval[2], oval[2];
-
- set_reset = 1 - (simasel->hilite_ima->selected);
-
- getmouseco_areawin(mval);
- oval[0] = mval[0] + 1;
- oval[1] = 0; /* Just give it a value to stop warnings */
-
- while(get_mbut()&R_MOUSE) {
- getmouseco_areawin(mval);
- if ((oval[0] != mval[0]) || (oval[1] != mval[1])){
- simasel->mx = mval[0];
- simasel->my = mval[1];
-
- calc_hilite(simasel);
-
- if (simasel->hilite_ima){
- simasel->hilite_ima->selected = set_reset;
- scrarea_do_windraw(curarea);
- screen_swapbuffers();
+ SpaceImaSel *simasel= sa->spacedata.first;
+ rctf dispf;
+ rcti winrect;
+ struct direntry *file;
+ char path[FILE_MAX];
+ float tsize;
+ short ofsx=0;
+ short ofsy=0;
+ short ex, ey;
+ float scaledx, scaledy;
+ int index;
+
+ BLI_init_rctf(&dispf, 0.0f, (block->maxx - block->minx)-0.0f, 0.0f, (block->maxy - block->miny)-0.0f);
+ ui_graphics_to_window_rct(sa->win, &dispf, &winrect);
+
+ if (!simasel->img) {
+ BLI_join_dirfile(path, simasel->dir, simasel->file);
+ if (!BLI_exists(path))
+ return;
+
+ index = BIF_filelist_find(simasel->files, simasel->file);
+ if (index >= 0) {
+ file = BIF_filelist_file(simasel->files,index);
+ if (file->flags & IMAGEFILE || file->flags & MOVIEFILE) {
+ simasel->img = IMB_loadiffname(path, IB_rect);
+
+ if (simasel->img) {
+ tsize = MIN2(winrect.xmax - winrect.xmin,winrect.ymax - winrect.ymin);
+
+ if (simasel->img->x > simasel->img->y) {
+ scaledx = (float)tsize;
+ scaledy = ( (float)simasel->img->y/(float)simasel->img->x )*tsize;
+ ofsy = (scaledx - scaledy) / 2.0;
+ ofsx = 0;
+ }
+ else {
+ scaledy = (float)tsize;
+ scaledx = ( (float)simasel->img->x/(float)simasel->img->y )*tsize;
+ ofsx = (scaledy - scaledx) / 2.0;
+ ofsy = 0;
+ }
+ ex = (short)scaledx;
+ ey = (short)scaledy;
+
+ IMB_scaleImBuf(simasel->img, ex, ey);
+ }
}
- oval[0] = mval[0];
- oval[1] = mval[1];
}
}
+ if (simasel->img == NULL)
+ return;
+ if(simasel->img->rect==NULL)
+ return;
+
+ /* correction for gla draw */
+ BLI_translate_rcti(&winrect, -curarea->winrct.xmin, -curarea->winrct.ymin);
+
+ glaDefine2DArea(&sa->winrct);
+ glaDrawPixelsSafe(winrect.xmin+ofsx, winrect.ymin+ofsy, simasel->img->x, simasel->img->y, simasel->img->x, GL_RGBA, GL_UNSIGNED_BYTE, simasel->img->rect);
}
-void move_imadir_sli(SpaceImaSel *simasel)
+static void imasel_panel_image(ScrArea *sa, short cntrl)
{
-
- short mval[2], lval[2], fh;
- float rh;
-
- getmouseco_areawin(mval);
-
- if ((mval[0] > simasel->dirsli_sx) &&
- (mval[0] < simasel->dirsli_ex) &&
- (mval[1] > simasel->dirsli_ey - simasel->dirsli_h) &&
- (mval[1] < simasel->dirsli_ey) ){
-
- /* extactly in the slider */
- fh = simasel->dirsli_ey - mval[1];
- lval[1]=1;
- while(get_mbut()&L_MOUSE) {
- getmouseco_areawin(mval);
- if (mval[1] != lval[1]){
-
- rh = (float)(simasel->dsey - mval[1] - fh - simasel->dssy) / (simasel->dsdh - simasel->dirsli_h);
-
- simasel->topdir = 1 + rh * (simasel->totaldirs - simasel->dirsli_lines);
-
- scrarea_do_windraw(curarea);
- uiEmboss(simasel->dirsli_sx, simasel->dirsli_ey - simasel->dirsli_h,
- simasel->dirsli_ex, simasel->dirsli_ey,1);
- screen_swapbuffers();
- lval[1] = mval[1];
- }
- }
- }else{
- if (mval[1] < simasel->dirsli_ey - simasel->dirsli_h)
- simasel->topdir += (simasel->dirsli_lines - 1);
- else
- simasel->topdir -= (simasel->dirsli_lines - 1);
-
- while(get_mbut()&L_MOUSE) { }
+ uiBlock *block;
+ SpaceImaSel *simasel= sa->spacedata.first;
+ short w = 300;
+ short h = 300;
+ short offsx, offsy;
+
+ if (simasel->img) {
+ w = simasel->img->x;
+ h = simasel->img->y;
}
+
+ offsx = -150 + (simasel->v2d.mask.xmax - simasel->v2d.mask.xmin)/2;
+ offsy = -150 + (simasel->v2d.mask.ymax - simasel->v2d.mask.ymin)/2;
+
+ block= uiNewBlock(&curarea->uiblocks, "imasel_panel_image", UI_EMBOSS, UI_HELV, curarea->win);
+ uiPanelControl(UI_PNL_SOLID | UI_PNL_CLOSE | cntrl);
+ uiSetPanelHandler(IMASEL_HANDLER_IMAGE); // for close and esc
+ if(uiNewPanel(curarea, block, "Image Preview", "Image Browser", offsx, offsy, w, h)==0)
+ return;
+ uiBlockSetDrawExtraFunc(block, imasel_imgdraw);
}
-void move_imafile_sli(SpaceImaSel *simasel)
+static void imasel_blockhandlers(ScrArea *sa)
{
- short mval[2], cmy, omy = 0;
- short ssl, sdh, ssv;
-
- getmouseco_areawin(mval);
- cmy = mval[1];
-
- if ((mval[0] > simasel->imasli_sx) &&
- (mval[0] < simasel->imasli_ex) &&
- (mval[1] > simasel->imasli_ey - simasel->imasli_h) &&
- (mval[1] < simasel->imasli_ey) ){
+ SpaceImaSel *simasel= sa->spacedata.first;
+ short a;
- ssv = simasel->fsey - simasel->imasli_ey - 2;
+ for(a=0; a<SPACE_MAXHANDLER; a+=2) {
+ switch(simasel->blockhandler[a]) {
+
+ case IMASEL_HANDLER_IMAGE:
+ imasel_panel_image(sa, simasel->blockhandler[a+1]);
+ break;
- while(get_mbut() & L_MOUSE) {
- getmouseco_areawin(mval);
- if (mval[1] != omy){
- sdh = simasel->fsdh - simasel->imasli_h;
- ssl = cmy - mval[1] + ssv;
-
- if (ssl < 0) { ssl = 0; }
- if (ssl > sdh) { ssl = sdh; }
-
- simasel->image_slider = ssl / (float)sdh;
-
- scrarea_do_windraw(curarea);
- uiEmboss(simasel->imasli_sx, simasel->imasli_ey - simasel->imasli_h,
- simasel->imasli_ex, simasel->imasli_ey, 1);
-
- screen_swapbuffers();
- omy = mval[1];
- }
}
- }else{
- while(get_mbut() & L_MOUSE) { }
+ /* clear action value for event */
+ simasel->blockhandler[a+1]= 0;
}
+ uiDrawBlocksPanels(sa, 0);
}
-void ima_select_all(SpaceImaSel *simasel)
+
+static void draw_imasel_buttons(ScrArea *sa, SpaceImaSel* simasel)
{
- OneSelectableIma *ima;
- int reselect = 0;
-
- ima = simasel->first_sel_ima;
- if (!ima) return;
-
- while(ima){
- if (ima->selected == 1) reselect = 1;
- ima = ima->next;
- }
- ima = simasel->first_sel_ima;
- if (reselect == 1){
- while(ima){
- ima->selected = 0;
- ima = ima->next;
- }
- }else{
- while(ima){
- ima->selected = 1;
- ima = ima->next;
+ uiBlock *block;
+ int loadbutton;
+ char name[20];
+ char *menu;
+ float slen;
+ float parentbut_width = 20;
+ float bookmarkbut_width = 0.0f;
+ int filebuty1, filebuty2;
+
+ float xmin = simasel->v2d.mask.xmin + 10;
+ float xmax = simasel->v2d.mask.xmax - 10;
+
+ filebuty1= simasel->v2d.mask.ymax - IMASEL_BUTTONS_HEIGHT;
+ filebuty2= filebuty1+IMASEL_BUTTONS_HEIGHT/2 -6;
+
+ /* HEADER */
+ sprintf(name, "win %d", sa->win);
+ block = uiNewBlock(&sa->uiblocks, name, UI_EMBOSS, UI_HELV, sa->win);
+
+ uiSetButLock( BIF_filelist_gettype(simasel->files)==FILE_MAIN && simasel->returnfunc, NULL);
+
+ /* space available for load/save buttons? */
+ slen = BIF_GetStringWidth(G.font, simasel->title, simasel->aspect);
+ loadbutton= slen > 60 ? slen + 20 : 80; /* MAX2(80, 20+BIF_GetStringWidth(G.font, simasel->title)); */
+ if(simasel->v2d.mask.xmax-simasel->v2d.mask.xmin > loadbutton+20) {
+ if(simasel->title[0]==0) {
+ loadbutton= 0;
}
}
-}
+ else {
+ loadbutton= 0;
+ }
-void pibplay(SpaceImaSel *simasel)
-{
- OneSelectableIma *ima;
- int sx= 8, sy= 8;
-
- ima = simasel->first_sel_ima;
- if (!ima) return ;
-
- sx = curarea->winrct.xmin + 8;
- sy = curarea->winrct.ymin + 8;
-
- while(!(get_mbut()&L_MOUSE)){
- scrarea_do_windraw(curarea);
-
- lrectwrite(sx, sy, sx+ima->dw-1, sy+ima->dh-1, ima->pict->rect);
-
- ima = ima->next;
- if (!ima) ima = simasel->first_sel_ima;
- screen_swapbuffers();
+ menu= fsmenu_build_menu();
+
+ if (menu[0]) {
+ bookmarkbut_width = parentbut_width;
+ }
+
+ uiDefBut(block, TEX, B_FS_FILENAME,"", xmin+parentbut_width+bookmarkbut_width+2, filebuty1, xmax-xmin-loadbutton-parentbut_width-bookmarkbut_width, 21, simasel->file, 0.0, (float)FILE_MAXFILE-1, 0, 0, "");
+ uiDefBut(block, TEX, B_FS_DIRNAME,"", xmin+parentbut_width, filebuty2, xmax-xmin-loadbutton-parentbut_width, 21, simasel->dir, 0.0, (float)FILE_MAXFILE-1, 0, 0, "");
+
+ if(loadbutton) {
+ uiSetCurFont(block, UI_HELV);
+ uiDefBut(block, BUT,B_FS_LOAD, simasel->title, xmax-loadbutton, filebuty2, loadbutton, 21, simasel->dir, 0.0, (float)FILE_MAXFILE-1, 0, 0, "");
+ uiDefBut(block, BUT,B_FS_CANCEL, "Cancel", xmax-loadbutton, filebuty1, loadbutton, 21, simasel->file, 0.0, (float)FILE_MAXFILE-1, 0, 0, "");
}
+
+ if(menu[0]) { // happens when no .Bfs is there, and first time browse
+ uiDefButS(block, MENU,B_FS_DIR_MENU, menu, xmin, filebuty1, parentbut_width, 21, &simasel->menu, 0, 0, 0, 0, "");
+ uiDefBut(block, BUT, B_FS_BOOKMARK, "B", xmin+22, filebuty1, bookmarkbut_width, 21, 0, 0, 0, 0, 0, "Bookmark current directory");
+ }
+ MEM_freeN(menu);
+
+ uiDefBut(block, BUT, B_FS_PARDIR, "P", xmin, filebuty2, parentbut_width, 21, 0, 0, 0, 0, 0, "Move to the parent directory (PKEY)");
+
+ uiDrawBlock(block);
}
@@ -860,65 +662,71 @@ void pibplay(SpaceImaSel *simasel)
void drawimaselspace(ScrArea *sa, void *spacedata)
{
- SpaceImaSel *simasel;
- simasel= curarea->spacedata.first;
+ float col[3];
+ SpaceImaSel *simasel= curarea->spacedata.first;
- /* ortho: xmin xmax, ymin, ymax! */
- myortho2(-0.375, (float)(curarea->winx)-0.375, -0.375, (float)(curarea->winy)-0.375);
+ BIF_GetThemeColor3fv(TH_BACK, col);
+ glClearColor(col[0], col[1], col[2], 0.0);
+ glClear(GL_COLOR_BUFFER_BIT);
- if (simasel->fase == 0){
- BLI_cleanup_dir(G.sce, simasel->dir);
- clear_ima_dir(simasel);
- }
+ /* HACK: somehow when going fullscreen, v2d isn't set correctly */
+ simasel->v2d.cur.xmin= simasel->v2d.cur.ymin= 0.0f;
+ simasel->v2d.cur.xmax= sa->winx;
+ simasel->v2d.cur.ymax= sa->winy;
+ simasel->v2d.tot= simasel->v2d.cur;
+ test_view2d(G.v2d, sa->winx, sa->winy);
- if (!bitset(simasel->fase, IMS_KNOW_DIR)){
- if(simasel->firstdir) free_ima_dir(simasel->firstdir);
- if(simasel->firstfile) free_ima_dir(simasel->firstfile);
- simasel->firstdir = 0;
- simasel->firstfile = 0;
+ calc_imasel_rcts(simasel, sa->winx, sa->winy);
+
+ myortho2(simasel->v2d.cur.xmin, simasel->v2d.cur.xmax, simasel->v2d.cur.ymin, simasel->v2d.cur.ymax);
+ bwin_clear_viewmat(sa->win); /* clear buttons view */
+ glLoadIdentity();
- if (get_ima_dir(simasel->dir, IMS_DIR, &simasel->totaldirs, &simasel->firstdir) < 0){
- /* error */
- strcpy(simasel->dir, simasel->dor);
- get_ima_dir(simasel->dir, IMS_DIR, &simasel->totaldirs, &simasel->firstdir);
- }
-
- if (get_ima_dir(simasel->dir, IMS_FILE, &simasel->totalfiles, &simasel->firstfile) < 0){
- /* error */
- strcpy(simasel->file, simasel->fole);
- get_ima_dir(simasel->dir, IMS_FILE, &simasel->totalfiles, &simasel->firstfile);
- }
-
- simasel->topdir = 0;
- simasel->topfile = 0;
- simasel->fase |= IMS_KNOW_DIR;
-
- check_for_pib(simasel);
-
- strcpy(simasel->fole, simasel->file);
- strcpy(simasel->dor, simasel->dir);
- }
-
- if (!bitset(simasel->fase, IMS_FOUND_BIP)){
- /* Make the first Bip file ever in this directory */
- if ( !bitset(simasel->fase, IMS_KNOW_INF)){
- if (!bitset(simasel->fase, IMS_DOTHE_INF)){
- if(simasel->first_sel_ima) free_sel_ima(simasel->first_sel_ima);
- simasel->first_sel_ima = 0;
- simasel->fase |= IMS_DOTHE_INF;
- addafterqueue(curarea->win, AFTERIMASELIMA, 1);
- }
- }
- }else{
- if (!bitset(simasel->fase, IMS_KNOW_BIP)){
- addafterqueue(curarea->win, AFTERPIBREAD, 1);
- }
+ /* warning; blocks need to be freed each time, handlers dont remove */
+ uiFreeBlocksWin(&sa->uiblocks, sa->win);
+
+ /* aspect+font, set each time */
+ simasel->aspect= (simasel->v2d.cur.xmax - simasel->v2d.cur.xmin)/((float)sa->winx);
+ simasel->curfont= uiSetCurFont_ext(simasel->aspect);
+
+ if (!simasel->files) {
+ simasel->files = BIF_filelist_new();
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ BIF_filelist_settype(simasel->files, simasel->type);
}
+
+ /* Buttons */
+ draw_imasel_buttons(sa, simasel);
- make_sima_area(simasel);
- calc_hilite(simasel);
- draw_sima_area(simasel);
+ /* scrollbar */
+ draw_imasel_scroll(simasel);
+
+ /* bookmarks */
+ draw_imasel_bookmarks(sa, simasel);
+
+ uiEmboss(simasel->viewrect.xmin, simasel->viewrect.ymin, simasel->v2d.mask.xmax-TILE_BORDER_X, simasel->viewrect.ymax, 1);
+
+
+ glScissor(sa->winrct.xmin + simasel->viewrect.xmin ,
+ sa->winrct.ymin + simasel->viewrect.ymin,
+ simasel->viewrect.xmax - simasel->viewrect.xmin ,
+ simasel->viewrect.ymax - simasel->viewrect.ymin);
+
+ /* previews */
+ draw_imasel_previews(sa, simasel);
+ /* BIF_ThemeColor(TH_HEADER);*/
+ /* glRecti(simasel->viewrect.xmin, simasel->viewrect.ymin, simasel->viewrect.xmax, simasel->viewrect.ymax);*/
+
+ /* restore viewport (not needed yet) */
+ mywinset(sa->win);
+
+ /* ortho at pixel level curarea */
+ myortho2(-0.375, curarea->winx-0.375, -0.375, curarea->winy-0.375);
+
+ draw_area_emboss(sa);
+
+ imasel_blockhandlers(sa);
+
curarea->win_swap= WIN_BACK_OK;
}
-
diff --git a/source/blender/src/drawnode.c b/source/blender/src/drawnode.c
index d9878d40d8e..d903d74681b 100644
--- a/source/blender/src/drawnode.c
+++ b/source/blender/src/drawnode.c
@@ -1773,37 +1773,6 @@ static void draw_nodespace_back(ScrArea *sa, SpaceNode *snode)
}
}
-static void nodeshadow(rctf *rct, float radius, float aspect, int select)
-{
- float rad;
- float a;
- char alpha= 2;
-
- glEnable(GL_BLEND);
-
- if(radius > (rct->ymax-rct->ymin-10.0f)/2.0f)
- rad= (rct->ymax-rct->ymin-10.0f)/2.0f;
- else
- rad= radius;
-
- if(select) a= 10.0f*aspect; else a= 7.0f*aspect;
- for(; a>0.0f; a-=aspect) {
- /* alpha ranges from 2 to 20 or so */
- glColor4ub(0, 0, 0, alpha);
- alpha+= 2;
-
- gl_round_box(GL_POLYGON, rct->xmin - a, rct->ymin - a, rct->xmax + a, rct->ymax-10.0f + a, rad+a);
- }
-
- /* outline emphasis */
- glEnable( GL_LINE_SMOOTH );
- glColor4ub(0, 0, 0, 100);
- gl_round_box(GL_LINE_LOOP, rct->xmin-0.5f, rct->ymin-0.5f, rct->xmax+0.5f, rct->ymax+0.5f, radius);
- glDisable( GL_LINE_SMOOTH );
-
- glDisable(GL_BLEND);
-}
-
/* nice AA filled circle */
static void socket_circle_draw(float x, float y, float size, int type, int select)
{
@@ -2148,7 +2117,7 @@ static void node_draw_basis(ScrArea *sa, SpaceNode *snode, bNode *node)
int ofs, color_id= node_get_colorid(node);
uiSetRoundBox(15-4);
- nodeshadow(rct, BASIS_RAD, snode->aspect, node->flag & SELECT);
+ ui_dropshadow(rct, BASIS_RAD, snode->aspect, node->flag & SELECT);
/* header */
if(color_id==TH_NODE)
@@ -2352,7 +2321,7 @@ void node_draw_hidden(SpaceNode *snode, bNode *node)
/* shadow */
uiSetRoundBox(15);
- nodeshadow(rct, hiddenrad, snode->aspect, node->flag & SELECT);
+ ui_dropshadow(rct, hiddenrad, snode->aspect, node->flag & SELECT);
/* body */
BIF_ThemeColor(color_id);
diff --git a/source/blender/src/editimasel.c b/source/blender/src/editimasel.c
index f3f9aa31d07..bb56eb37288 100644
--- a/source/blender/src/editimasel.c
+++ b/source/blender/src/editimasel.c
@@ -43,411 +43,1080 @@
#include <sys/times.h>
#endif
-#include "PIL_time.h"
+#include "MEM_guardedalloc.h"
+
+#include "BKE_global.h"
+#include "BKE_library.h"
+#include "BKE_main.h"
+#include "BKE_depsgraph.h"
+#include "BKE_utildefines.h"
#include "BLI_blenlib.h"
#include "BLI_arithb.h"
+#include "BLI_storage_types.h"
-#include "DNA_screen_types.h"
+#ifdef WIN32
+#include "BLI_winstuff.h"
+#endif
+
+#include "DNA_armature_types.h"
+#include "DNA_action_types.h"
+#include "DNA_curve_types.h"
+#include "DNA_image_types.h"
+#include "DNA_ipo_types.h"
+#include "DNA_material_types.h"
+#include "DNA_mesh_types.h"
+#include "DNA_object_types.h"
+#include "DNA_texture_types.h"
#include "DNA_space_types.h"
+#include "DNA_scene_types.h"
+#include "DNA_screen_types.h"
#include "DNA_userdef_types.h"
+#include "DNA_vfont_types.h"
+#include "DNA_view3d_types.h"
-#include "BKE_global.h"
-#include "BIF_fsmenu.h"
+#include "BIF_filelist.h"
+#include "BIF_space.h"
#include "BIF_screen.h"
#include "BIF_interface.h"
-#include "BIF_imasel.h"
#include "BIF_mywindow.h"
+#include "BIF_imasel.h"
+#include "BIF_gl.h"
+#include "BIF_fsmenu.h"
+#include "BIF_editview.h"
#include "BIF_toolbox.h"
-#include "BSE_filesel.h"
+#include "BLO_readfile.h"
+
+#include "BPI_script.h"
+
+#include "BSE_drawipo.h"
#include "BSE_drawimasel.h"
+#include "BSE_edit.h"
-#include "BDR_editcurve.h"
+#include "IMB_imbuf.h"
+#include "IMB_imbuf_types.h"
#include "blendef.h"
#include "mydevice.h"
-#define XIC 20
-#define YIC 21
+/* for events */
+#define NOTACTIVE 0
+#define ACTIVATE 1
+#define INACTIVATE 2
+/* for state of file */
+#define ACTIVE 2
-/* GLOBALS */
-extern char *fsmenu;
+static void imasel_select_objects(SpaceImaSel *simasel);
-void winqreadimaselspace(ScrArea *, void *, BWinEvent *);
+static int imasel_has_func(SpaceImaSel *simasel)
+{
+ if(simasel->returnfunc || simasel->returnfunc_event || simasel->returnfunc_args)
+ return 1;
+ return 0;
+}
-void winqreadimaselspace(ScrArea *sa, void *spacedata, BWinEvent *evt)
+/* ugly, needs to be moved to platform specific files - elubie */
+#if defined WIN32 || defined __BeOS
+static int fnmatch(const char *pattern, const char *string, int flags)
+{
+ return 0;
+}
+#else
+ #include <fnmatch.h>
+#endif
+
+/**************** IMAGESELECT ******************************/
+
+/* the complete call; pulldown menu, and three callback types */
+static void activate_imageselect_(int type, char *title, char *file, short *menup, char *pupmenu,
+ void (*func)(char *),
+ void (*func_event)(unsigned short),
+ void (*func_args)(char *, void *arg1, void *arg2),
+ void *arg1, void *arg2)
{
- unsigned short event= evt->event;
- short val= evt->val;
SpaceImaSel *simasel;
+ char group[24], name[FILE_MAX], temp[FILE_MAX];
- short mval[2];
- short area_event;
- short queredraw = 0;
- int ret = 0;
- char name[256];
- char *selname;
- static double prevtime=0;
+ if(curarea==0) return;
+ if(curarea->win==0) return;
+ newspace(curarea, SPACE_IMASEL);
+ scrarea_queue_winredraw(curarea);
+
+ /* sometime double, when area already is SPACE_IMASEL with a different file name */
+ if(curarea->headwin) addqueue(curarea->headwin, CHANGED, 1);
+
+ name[2]= 0;
+ BLI_strncpy(name, file, sizeof(name));
- if(val==0) return;
simasel= curarea->spacedata.first;
+
+ simasel->returnfunc= func;
+ simasel->returnfunc_event= func_event;
+ simasel->returnfunc_args= func_args;
+ simasel->arg1= arg1;
+ simasel->arg2= arg2;
- area_event = 0;
- getmouseco_areawin(mval);
- simasel->mx= mval[0];
- simasel->my= mval[1];
+ simasel->type= type;
+ simasel->scrollpos = 0.0f;
+
+ if(simasel->pupmenu)
+ MEM_freeN(simasel->pupmenu);
+ simasel->pupmenu= pupmenu;
+ simasel->menup= menup;
+
+ /* sfile->act is used for databrowse: double names of library objects */
+ simasel->active_file= -1;
+
+ if(!simasel->files) {
+ simasel->files = BIF_filelist_new();
+ }
+
+ if(BLI_convertstringcode(name, G.sce, G.scene->r.cfra)) simasel->flag |= FILE_STRINGCODE;
+ else simasel->flag &= ~FILE_STRINGCODE;
+
+ if (U.uiflag & USER_HIDE_DOT)
+ simasel->flag |= FILE_HIDE_DOT;
+
+ if(type==FILE_MAIN) {
+ char *groupname;
+
+ BLI_strncpy(simasel->file, name+2, sizeof(simasel->file));
+
+ groupname = BLO_idcode_to_name( GS(name) );
+ if (groupname) {
+ BLI_strncpy(simasel->dir, groupname, sizeof(simasel->dir) - 1);
+ strcat(simasel->dir, "/");
+ }
+
+ /* free all */
+ if (simasel->files) {
+ BIF_filelist_freelib(simasel->files);
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ BIF_filelist_settype(simasel->files, type);
+ }
+ }
+ else if(type==FILE_LOADLIB) {
+ BLI_strncpy(simasel->dir, name, sizeof(simasel->dir));
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ if( BIF_filelist_islibrary(simasel->files, temp, group) ) {
+ /* force a reload of the library-filelist */
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_freelib(simasel->files);
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ BIF_filelist_settype(simasel->files, type);
+ }
+ else {
+ BLI_split_dirfile(file, temp, name);
+ BLI_strncpy(simasel->dir, temp, sizeof(simasel->dir));
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_freelib(simasel->files);
+ BIF_filelist_settype(simasel->files, type);
+ }
+ }
+ else { /* FILE_BLENDER */
+ BLI_split_dirfile(file, temp, name);
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_setdir(simasel->files, temp);
+ BIF_filelist_settype(simasel->files, type);
+
+ BLI_cleanup_dir(G.sce, simasel->dir);
+
+ /* free: filelist and libfiledata became incorrect */
+ BIF_filelist_freelib(simasel->files);
+ }
+ BLI_strncpy(simasel->title, title, sizeof(simasel->title));
+ /* filetoname= 1; */ /* TODO: elubie - check what this means */
+}
+
+void activate_imageselect(int type, char *title, char *file, void (*func)(char *))
+{
+ activate_imageselect_(type, title, file, NULL, NULL, func, NULL, NULL, NULL, NULL);
+}
+
+void activate_imageselect_menu(int type, char *title, char *file, char *pupmenu, short *menup, void (*func)(char *))
+{
+ activate_imageselect_(type, title, file, menup, pupmenu, func, NULL, NULL, NULL, NULL);
+}
+
+void activate_imageselect_args(int type, char *title, char *file, void (*func)(char *, void *, void *), void *arg1, void *arg2)
+{
+ activate_imageselect_(type, title, file, NULL, NULL, NULL, NULL, func, arg1, arg2);
+}
+
+void activate_databrowse_imasel(ID *id, int idcode, int fromcode, int retval, short *menup, void (*func)(unsigned short))
+{
+ ListBase *lb;
+ SpaceImaSel *simasel;
+ char str[32];
- if (simasel->desx > 0){
- if ( (mval[0] > simasel->dssx) && (mval[0] < simasel->dsex) && (mval[1] > simasel->dssy) && (mval[1] < simasel->dsey) ) area_event = IMS_INDIRSLI;
- if ( (mval[0] > simasel->desx) && (mval[0] < simasel->deex) && (mval[1] > simasel->desy) && (mval[1] < simasel->deey) ) area_event = IMS_INDIR;
+ if(id==NULL) {
+ lb= wich_libbase(G.main, idcode);
+ id= lb->first;
}
- if (simasel->fesx > 0){
- if ( (mval[0] > simasel->fssx) && (mval[0] < simasel->fsex) && (mval[1] > simasel->fssy) && (mval[1] < simasel->fsey) ) area_event = IMS_INFILESLI;
- if ( (mval[0] > simasel->fesx) && (mval[0] < simasel->feex) && (mval[1] > simasel->fesy) && (mval[1] < simasel->feey) ) area_event = IMS_INFILE;
- }
- if( event!=RETKEY && event!=PADENTER)
- if( uiDoBlocks(&curarea->uiblocks, event)!=UI_NOTHING ) event= 0;
-
- switch(event) {
- case AFTERPIBREAD:
- get_pib_file(simasel);
- queredraw = 1;
- break;
-
- case AFTERIMASELIMA:
- if (bitset(simasel->fase, IMS_DOTHE_INF)){
- get_file_info(simasel);
-
- if (!bitset(simasel->fase, IMS_KNOW_INF)){
- addafterqueue(curarea->win, AFTERIMASELIMA, 1);
-
- }else{
- simasel->subfase = 0;
- simasel->imafase = 0;
- simasel->fase |= IMS_DOTHE_IMA;
- addafterqueue(curarea->win, AFTERIMASELGET, 1);
+ if(id) BLI_strncpy(str, id->name, sizeof(str));
+ else return;
+
+ activate_imageselect_(FILE_MAIN, "SELECT DATABLOCK", str, menup, NULL, NULL, func, NULL, NULL, NULL);
+
+ simasel= curarea->spacedata.first;
+ simasel->retval= retval;
+ simasel->menup= menup;
+
+ BIF_filelist_setipotype(simasel->files, fromcode);
+ BIF_filelist_hasfunc(simasel->files, imasel_has_func(simasel));
+}
+
+
+static void set_active_file(SpaceImaSel *simasel, short x, short y)
+{
+ short tilex, tiley;
+ int active_tile;
+ int active_file;
+ int stridex;
+ struct direntry* file;
+ rcti viewrect = simasel->viewrect;
+ int fileoffset;
+ int rowoffset;
+ int rowleftover;
+ float scrollofs;
+ int numfiles;
+ int tilewidth = simasel->prv_w + TILE_BORDER_X*4;
+ int tileheight = simasel->prv_h + TILE_BORDER_Y*4 + U.fontsize;
+
+ numfiles = BIF_filelist_numfiles(simasel->files);
+
+ if (simasel->numtilesx > 0) {
+ fileoffset = numfiles*(simasel->scrollpos / simasel->scrollarea) + 0.5;
+ rowoffset = (fileoffset / simasel->numtilesx)*simasel->numtilesx;
+ rowleftover = fileoffset % simasel->numtilesx;
+ scrollofs = (float)tileheight*(float)rowleftover/(float)simasel->numtilesx;
+
+ stridex = (viewrect.xmax - viewrect.xmin) / (tilewidth);
+ tilex = ( (x-viewrect.xmin)) / (tilewidth);
+ tiley = (viewrect.ymax - viewrect.ymin + scrollofs - y) / (tileheight);
+ if (tilex >= simasel->numtilesx) tilex = simasel->numtilesx-1;
+ if (tiley >= simasel->numtilesy+1) tiley = simasel->numtilesy;
+ if (tilex < 0) tilex=0;
+ if (tiley < 0) tiley = 0;
+ active_tile = tilex + stridex*tiley;
+ active_file = rowoffset + active_tile;
+
+ if (active_file >= 0 && active_file < BIF_filelist_numfiles(simasel->files) )
+ {
+ simasel->active_file = active_file;
+ if (simasel->selstate & ACTIVATE) {
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+ file->flags |= ACTIVE;
}
+ } else {
+ simasel->active_file = -1;
+ }
+ } else {
+ simasel->active_file = -1;
+ }
+}
+
+static void set_active_bookmark(SpaceImaSel *simasel, short y)
+{
+ int nentries = fsmenu_get_nentries();
+ short posy = simasel->bookmarkrect.ymax - U.fontsize*3/2 - TILE_BORDER_Y - y;
+ simasel->active_bookmark = ((float)posy / (U.fontsize*3.0f/2.0f)) + 0.5;
+ if (simasel->active_bookmark < 0 || simasel->active_bookmark > nentries) {
+ simasel->active_bookmark = -1;
+ }
+}
+
+static void imasel_prevspace()
+{
+ SpaceImaSel *simasel;
+
+ simasel= curarea->spacedata.first;
+
+ /* cleanup */
+ if(simasel->spacetype==SPACE_IMASEL) {
+ if(simasel->pupmenu) {
+ MEM_freeN(simasel->pupmenu);
+ simasel->pupmenu= NULL;
+ }
+ }
+
+ if(simasel->next) {
+
+ BLI_remlink(&curarea->spacedata, simasel);
+ BLI_addtail(&curarea->spacedata, simasel);
+
+ simasel= curarea->spacedata.first;
+
+ if (simasel->spacetype == SPACE_SCRIPT) {
+ SpaceScript *sc = (SpaceScript *)simasel;
+ if (sc->script) sc->script->flags &=~SCRIPT_FILESEL;
}
- break;
- case AFTERIMASELGET:
- if (bitset(simasel->fase, IMS_DOTHE_IMA)){
- get_next_image(simasel);
- if (simasel->ima_redraw > 0){
- double newtime = PIL_check_seconds_timer();
- if ((newtime - prevtime) > 0.03) {
- simasel->ima_redraw = 0;
- queredraw = 1;
- prevtime = newtime;
+
+ newspace(curarea, simasel->spacetype);
+ }
+ else newspace(curarea, SPACE_INFO);
+}
+
+static void free_imasel_spec(char *dir)
+{
+ /* all filesels with 'dir' are freed */
+ bScreen *sc;
+
+ sc= G.main->screen.first;
+ while(sc) {
+ ScrArea *sa= sc->areabase.first;
+ while(sa) {
+ SpaceLink *sl= sa->spacedata.first;
+ while(sl) {
+ if(sl->spacetype==SPACE_FILE) {
+ SpaceImaSel *simasel= (SpaceImaSel*) sl;
+ if (BLI_streq(simasel->dir, dir)) {
+ BIF_filelist_free(simasel->files);
+ }
}
-
+ sl= sl->next;
}
- if (!bitset(simasel->fase, IMS_KNOW_IMA)){
- addafterqueue(curarea->win, AFTERIMASELGET, 1);
- }else{
- simasel->ima_redraw = 0;
- simasel->subfase = 0;
- simasel->imafase = 0;
- addqueue(curarea->win, AFTERIMAWRITE, 1);
- queredraw = 1;
+ sa= sa->next;
+ }
+ sc= sc->id.next;
+ }
+}
+
+static void do_library_append(SpaceImaSel *simasel)
+{
+ Library *lib;
+ char dir[FILE_MAXDIR], group[32];
+
+ if ( BIF_filelist_islibrary(simasel->files, dir, group)==0 ) {
+ error("Not a library");
+ } else if (!BIF_filelist_lib(simasel->files) ) {
+ error("Library not loaded");
+ } else if (group[0]==0) {
+ error("Nothing indicated");
+ } else if (BLI_streq(G.main->name, dir)) {
+ error("Cannot use current file as library");
+ } else {
+ Object *ob;
+ int idcode = BIF_groupname_to_code(group);
+
+ if((simasel->flag & FILE_LINK)==0) {
+ /* tag everything, all untagged data can be made local */
+ ID *id;
+ ListBase *lbarray[MAX_LIBARRAY];
+ int a;
+
+ a= set_listbasepointers(G.main, lbarray);
+ while(a--) {
+ for(id= lbarray[a]->first; id; id= id->next) id->flag |= LIB_APPEND_TAG;
}
}
- break;
- case AFTERIMAWRITE:
- if (bitset(simasel->fase, IMS_KNOW_IMA)){
- write_new_pib(simasel);
- queredraw = 1;
+
+ BIF_filelist_append_library(simasel->files, dir, simasel->file, simasel->flag, idcode);
+
+ /* DISPLISTS? */
+ ob= G.main->object.first;
+ while(ob) {
+ if(ob->id.lib) {
+ ob->recalc |= OB_RECALC;
+ }
+ ob= ob->id.next;
}
- break;
- case RIGHTMOUSE:
- if ((area_event == IMS_INFILE) && (simasel->hilite_ima)){
- select_ima_files(simasel);
- queredraw = 1;
+ /* and now find the latest append lib file */
+ lib= G.main->library.first;
+ while(lib) {
+ if (BLI_streq(dir, lib->filename)) break;
+ lib= lib->id.next;
}
- break;
- case UI_BUT_EVENT:
- /* bug: blender's interface kit also returns a '4'... what is it! */
+ /* make local */
+ if(lib) {
+ if((simasel->flag & FILE_LINK)==0)
+ all_local(lib,1);
+ }
- switch(val) {
- case 13: /* 'P' */
- imadir_parent(simasel);
- queredraw = 1;
-
- case 1: /* dir entry */
- BLI_cleanup_dir(G.sce, simasel->dir);
- clear_ima_dir(simasel);
- queredraw = 1;
- break;
+ DAG_scene_sort(G.scene);
+
+ /* in sfile->dir is the whole lib name */
+ BLI_strncpy(G.lib, simasel->dir, sizeof(G.lib) );
- case 3: /* fsmenu */
- selname= fsmenu_get_entry(simasel->fileselmenuitem-1);
- if (selname) {
- strcpy(simasel->dir, selname);
- BLI_cleanup_dir(G.sce, simasel->dir);
- clear_ima_dir(simasel);
- queredraw = 1;
- }
- break;
+ }
+}
- case 5:
- if (simasel->returnfunc) {
- char name[256];
- strcpy(name, simasel->dir);
- strcat(name, simasel->file);
- filesel_prevspace();
- simasel->returnfunc(name);
+/* NOTE: this is called for file read, after the execfunc no UI memory is valid! */
+static void imasel_execute(SpaceImaSel *simasel)
+{
+ struct direntry *file;
+ char name[FILE_MAX];
+ int a;
+ int n;
+
+ imasel_prevspace();
+
+ if(simasel->type==FILE_LOADLIB) {
+ if(simasel->flag & FILE_STRINGCODE) {
+ if (!G.relbase_valid) {
+ okee("You have to save the .blend file before using relative paths! Using absolute path instead.");
+ simasel->flag &= ~FILE_STRINGCODE;
}
- break;
- case 6:
- filesel_prevspace();
- break;
-
}
- break;
-
- case LEFTMOUSE:
- case MIDDLEMOUSE:
+
+ do_library_append(simasel);
+ BIF_undo_push("Append from file");
+ allqueue(REDRAWALL, 1);
+ }
+ else if(imasel_has_func(simasel)) {
+ fsmenu_insert_entry(simasel->dir, 1, 0);
- /* No button pressed */
- switch (area_event){
- case IMS_INDIRSLI:
- move_imadir_sli(simasel);
- queredraw = 1;
- break;
- case IMS_INFILESLI:
- move_imafile_sli(simasel);
- queredraw = 1;
- break;
- case IMS_INDIR:
- if (simasel->hilite > -1){
- change_imadir(simasel);
- queredraw = 1;
- }
- break;
- case IMS_INFILE:
- if (simasel->hilite_ima){
- strcpy(simasel->fole, simasel->hilite_ima->file_name);
- strcpy(simasel->file, simasel->hilite_ima->file_name);
-
- if (event == LEFTMOUSE) addqueue(curarea->win, IMALEFTMOUSE, 1);
-
- if ((event == MIDDLEMOUSE)&&(simasel->returnfunc)){
- strcpy(name, simasel->dir);
- strcat(name, simasel->file);
-
- if(simasel->mode & IMS_STRINGCODE) BLI_makestringcode(G.sce, name);
+ if(simasel->type==FILE_MAIN) { /* DATABROWSE */
+ if (simasel->menup) { /* with value pointing to ID block index */
+ int notfound = 1;
+
+ /* Need special handling since hiding .* datablocks means that
+ simasel->active_file is no longer the same as files->nr.
+
+ Also, toggle HIDE_DOT on and off can make simasel->active_file not longer
+ correct (meaning it doesn't point to the correct item in the filelist.
- filesel_prevspace();
- simasel->returnfunc(name);
+ simasel->file is always correct, so first with check if, for the item
+ corresponding to simasel->active_file, the name is the same.
+
+ If it isn't (or if simasel->active_file is not good), go over filelist and take
+ the correct one.
+
+ This means that selecting a datablock than hiding it makes it
+ unselectable. Not really a problem.
+
+ - theeth
+ */
+
+ *simasel->menup= -1;
+ n = BIF_filelist_numfiles(simasel->files);
+ if(simasel->files) {
+ if( (simasel->active_file>=0) && (simasel->active_file < n) ) {
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+ if ( strcmp(file->relname, simasel->file)==0) {
+ notfound = 0;
+ *simasel->menup= file->nr;
+ }
+ }
+ if (notfound) {
+ for(a=0; a<n; a++) {
+ file = BIF_filelist_file(simasel->files, a);
+ if( strcmp(file->relname, simasel->file)==0) {
+ *simasel->menup= file->nr;
+ break;
+ }
+ }
+ }
}
- queredraw = 1;
}
- break;
+ if(simasel->returnfunc_event)
+ simasel->returnfunc_event(simasel->retval);
+ else if(simasel->returnfunc_args)
+ simasel->returnfunc_args(NULL, simasel->arg1, simasel->arg2);
+ }
+ else {
+ if(strncmp(simasel->title, "Save", 4)==0) free_imasel_spec(simasel->dir);
+ if(strncmp(simasel->title, "Export", 6)==0) free_imasel_spec(simasel->dir);
+
+ BLI_strncpy(name, simasel->dir, sizeof(name));
+ strcat(name, simasel->file);
+
+ if(simasel->flag & FILE_STRINGCODE) {
+ if (!G.relbase_valid) {
+ /* skip save */
+ if(strncmp(simasel->title, "Save", 4)) {
+ okee("You have to save the .blend file before using relative paths! Using absolute path instead.");
+ simasel->flag &= ~FILE_STRINGCODE;
+ }
+ }
+ else {
+ BLI_makestringcode(G.sce, name);
+ }
+ }
+ if(simasel->returnfunc)
+ simasel->returnfunc(name);
+ else if(simasel->returnfunc_args)
+ simasel->returnfunc_args(name, simasel->arg1, simasel->arg2);
}
- break;
+ }
+}
+
+static void do_imasel_buttons(short event, SpaceImaSel *simasel)
+{
+ char butname[FILE_MAX];
- case MOUSEX:
- case MOUSEY:
- getmouseco_areawin(mval); /* local screen coordinates */
- calc_hilite(simasel);
- if (simasel->mouse_move_redraw ){
- simasel->mouse_move_redraw = 0;
- queredraw = 1;
+ if (event == B_FS_FILENAME) {
+ if (strchr(simasel->file, '*') || strchr(simasel->file, '?') || strchr(simasel->file, '[')) {
+ int i, match = FALSE;
+ struct direntry *file;
+ int n = BIF_filelist_numfiles(simasel->files);
+ for (i = 2; i < n; i++) {
+ file = BIF_filelist_file(simasel->files, i);
+ if (fnmatch(simasel->file, file->relname, 0) == 0) {
+ file->flags |= ACTIVE;
+ match = TRUE;
+ }
+ }
+ if (match) simasel->file[0] = '\0';
+ if(simasel->type==FILE_MAIN) imasel_select_objects(simasel);
+ scrarea_queue_winredraw(curarea);
}
- break;
+ }
+ else if(event== B_FS_DIRNAME) {
+ /* reuse the butname variable */
+ BLI_cleanup_dir(G.sce, simasel->dir);
+
+ BLI_make_file_string(G.sce, butname, simasel->dir, "");
+ BLI_strncpy(simasel->dir, butname, sizeof(simasel->dir));
+
+ /* strip the trailing slash if its a real dir */
+ if (strlen(butname)!=1)
+ butname[strlen(butname)-1]=0;
- case WHEELUPMOUSE:
- case WHEELDOWNMOUSE:
- switch(area_event){
- case IMS_INDIRSLI:
- case IMS_INDIR:
- if (simasel->dirsli){
- if (event == WHEELUPMOUSE) simasel->topdir -= U.wheellinescroll;
- if (event == WHEELDOWNMOUSE) simasel->topdir += U.wheellinescroll;
- queredraw = 1;
+ /* updating the directory in the filelist */
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+
+ if(simasel->type & FILE_UNIX) {
+ if (!BLI_exists(butname)) {
+ if (okee("Makedir")) {
+ BLI_recurdir_fileops(butname);
+ if (!BLI_exists(butname)) {
+ BIF_filelist_parent(simasel->files);
+ BLI_strncpy(simasel->dir, BIF_filelist_dir(simasel->files), 80);
+ }
+ } else {
+ BIF_filelist_parent(simasel->files);
+ BLI_strncpy(simasel->dir, BIF_filelist_dir(simasel->files), 80);
+ }
}
- break;
- case IMS_INFILESLI:
- case IMS_INFILE:
- if(simasel->imasli){
- if (event == WHEELUPMOUSE) simasel->image_slider -= 0.2 * simasel->slider_height;
- if (event == WHEELDOWNMOUSE) simasel->image_slider += 0.2 * simasel->slider_height;
-
- if(simasel->image_slider < 0.0) simasel->image_slider = 0.0;
- if(simasel->image_slider > 1.0) simasel->image_slider = 1.0;
- queredraw = 1;
- }
- break;
}
- break;
-
- case PAGEUPKEY:
- case PAGEDOWNKEY:
- switch(area_event){
- case IMS_INDIRSLI:
- case IMS_INDIR:
- if (simasel->dirsli){
- if (event == PAGEUPKEY) simasel->topdir -= (simasel->dirsli_lines - 1);
- if (event == PAGEDOWNKEY) simasel->topdir += (simasel->dirsli_lines - 1);
- queredraw = 1;
- }
- break;
- case IMS_INFILESLI:
- case IMS_INFILE:
- if(simasel->imasli){
- if (event == PAGEUPKEY) simasel->image_slider -= simasel->slider_height;
- if (event == PAGEDOWNKEY) simasel->image_slider += simasel->slider_height;
-
- if(simasel->image_slider < 0.0) simasel->image_slider = 0.0;
- if(simasel->image_slider > 1.0) simasel->image_slider = 1.0;
- queredraw = 1;
- }
- break;
+ BIF_filelist_free(simasel->files);
+ simasel->file[0] = '\0';
+ simasel->scrollpos = 0;
+ simasel->active_file = -1;
+ scrarea_queue_winredraw(curarea);
+ }
+ else if(event== B_FS_DIR_MENU) {
+ char *selected= fsmenu_get_entry(simasel->menu-1);
+
+ /* which string */
+ if (selected) {
+ BLI_strncpy(simasel->dir, selected, sizeof(simasel->dir));
+ BLI_make_exist(simasel->dir);
+ BLI_cleanup_dir(G.sce, simasel->dir);
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ simasel->file[0] = '\0';
+ simasel->scrollpos = 0;
+ simasel->active_file = -1;
+ scrarea_queue_winredraw(curarea);
}
- break;
+
+ simasel->active_file = -1;
+
+ }
+ else if(event== B_FS_PARDIR) {
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_parent(simasel->files);
+ BLI_strncpy(simasel->dir, BIF_filelist_dir(simasel->files), 80);
+ simasel->file[0] = '\0';
+ simasel->active_file = -1;
+ simasel->scrollpos = 0;
+ scrarea_queue_winredraw(curarea);
+ }
+ else if(event== B_FS_LOAD) {
+ if(simasel->type)
+ imasel_execute(simasel);
+ }
+ else if(event== B_FS_CANCEL)
+ imasel_prevspace();
+ else if(event== B_FS_LIBNAME) {
+ Library *lib= BLI_findlink(&G.main->library, simasel->menu);
+ if(lib) {
+ BLI_strncpy(simasel->dir, lib->filename, sizeof(simasel->dir));
+ BLI_make_exist(simasel->dir);
+ BLI_cleanup_dir(G.sce, simasel->dir);
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ simasel->file[0] = '\0';
+ simasel->scrollpos = 0;
+ simasel->active_file = -1;
+ scrarea_queue_winredraw(curarea);
+ }
+ } else if(event== B_FS_BOOKMARK) {
+ char name[FILE_MAX];
+ BLI_make_file_string(G.sce, name, BLI_gethome(), ".Bfs");
+ fsmenu_insert_entry(simasel->dir, 1, 1);
+ scrarea_queue_winredraw(curarea);
+ fsmenu_write_file(name);
+ }
+
+}
+
+static void imasel_home(ScrArea *sa, SpaceImaSel *simasel)
+{
+ simasel->v2d.cur.xmin= simasel->v2d.cur.ymin= 0.0f;
+ simasel->v2d.cur.xmax= sa->winx;
+ simasel->v2d.cur.ymax= sa->winy;
- case HOMEKEY:
- simasel->image_slider = 0.0;
- queredraw = 1;
- break;
-
- case ENDKEY:
- simasel->image_slider = 1.0;
- queredraw = 1;
- break;
+ simasel->v2d.tot= simasel->v2d.cur;
+ test_view2d(G.v2d, sa->winx, sa->winy);
+
+}
+
+static struct direntry* get_hilited_entry(SpaceImaSel *simasel)
+{
+ struct direntry *file;
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+ return file;
+}
+
+static void do_filescroll(SpaceImaSel *simasel)
+{
+ short mval[2], oldy, yo;
+ float scrollarea, scrollstep;
+
+ /* for beauty */
+ scrarea_do_windraw(curarea);
+ screen_swapbuffers();
+
+ getmouseco_areawin(mval);
+ oldy= yo= mval[1];
+
+ while(get_mbut()&L_MOUSE) {
+ getmouseco_areawin(mval);
+
+ if(yo!=mval[1]) {
+ scrollarea = ((float)simasel->v2d.vert.ymax - (float)simasel->v2d.vert.ymin);
+ scrollstep = yo - mval[1];
+ simasel->scrollpos += scrollstep;
- case AKEY:
- if (G.qual == 0){
- ima_select_all(simasel);
- queredraw = 1;
- }
- break;
+ if (simasel->scrollpos<0)
+ simasel->scrollpos=0;
+ if (simasel->scrollpos > scrollarea - simasel->scrollheight)
+ simasel->scrollpos = scrollarea - simasel->scrollheight;
+ scrarea_do_windraw(curarea);
+ screen_swapbuffers();
- case IKEY:
- if ((G.qual == 0)&&(simasel->file)){
- sprintf(name, "$IMAGEEDITOR %s%s", simasel->dir, simasel->file);
- system(name);
- queredraw = 1;
+ yo= mval[1];
}
+ else BIF_wait_for_statechange();
+ }
- break;
+ /* for beauty */
+ scrarea_do_windraw(curarea);
+ screen_swapbuffers();
- case PKEY:
- if(G.qual & LR_SHIFTKEY) {
- extern char bprogname[]; /* usiblender.c */
-#ifdef WIN32
- sprintf(name, "%s -a \"%s%s\"", bprogname, simasel->dir, simasel->file);
-#else
- sprintf(name, "\"%s\" -a \"%s%s\"", bprogname, simasel->dir, simasel->file);
-#endif
- system(name);
- }
- if(G.qual & LR_CTRLKEY) {
- if(bitset(simasel->fase, IMS_KNOW_IMA)) pibplay(simasel);
+}
+
+/* ******************* DATA SELECT ********************* */
+
+static void imasel_select_objects(SpaceImaSel *simasel)
+{
+ Object *ob;
+ Base *base;
+ Scene *sce;
+ struct direntry* file;
+ int a;
+ int totfile;
+
+ /* only when F4 DATABROWSE */
+ if(imasel_has_func(simasel)) return;
+
+ totfile = BIF_filelist_numfiles(simasel->files);
+
+ if( strcmp(simasel->dir, "Object/")==0 ) {
+ for(a=0; a<totfile; a++) {
+ file = BIF_filelist_file(simasel->files, a);
+ ob= (Object *)file->poin;
+
+ if(ob) {
+ if(file->flags & ACTIVE) ob->flag |= SELECT;
+ else ob->flag &= ~SELECT;
+ }
+
}
- if (G.qual == 0){
- imadir_parent(simasel);
- BLI_cleanup_dir(G.sce, simasel->dir);
- clear_ima_dir(simasel);
- queredraw = 1;
+ base= FIRSTBASE;
+ while(base) {
+ base->flag= base->object->flag;
+ base= base->next;
}
- break;
+ countall();
+ allqueue(REDRAWVIEW3D, 0);
+ allqueue(REDRAWOOPS, 0);
+ }
+ else if( strcmp(simasel->dir, "Scene/")==0 ) {
- case RKEY:
- case XKEY:
- if (simasel->hilite_ima){
- strcpy(name, simasel->dir);
- strcat(name, simasel->hilite_ima->file_name);
-
- if( okee("Delete %s", name) ) {
- ret = BLI_delete(name, 0, 0);
- if (ret) {
- error("Command failed, see console");
- } else {
- clear_ima_dir(simasel);
- queredraw = 1;
- }
+ for(a=0; a<totfile; a++) {
+ file = BIF_filelist_file(simasel->files, a);
+ sce= (Scene *)file->poin;
+ if(sce) {
+ if(file->flags & ACTIVE) sce->r.scemode |= R_BG_RENDER;
+ else sce->r.scemode &= ~R_BG_RENDER;
}
+
}
- break;
+ allqueue(REDRAWBUTSSCENE, 0);
+ }
+}
- case PADPLUSKEY:
- case EQUALKEY:
- BLI_newname(simasel->file, +1);
- queredraw = 1;
- break;
-
- case PADMINUS:
- case MINUSKEY:
- BLI_newname(simasel->file, -1);
- queredraw = 1;
- break;
-
- case BACKSLASHKEY:
- case SLASHKEY:
-#ifdef WIN32
- strcpy(simasel->dir, "\\");
-#else
- strcpy(simasel->dir, "/");
-#endif
- clear_ima_dir(simasel);
- simasel->image_slider = 0.0;
- queredraw = 1;
- break;
-
- case PERIODKEY:
- clear_ima_dir(simasel);
- queredraw = 1;
- break;
+static void active_imasel_object(SpaceImaSel *simasel)
+{
+ Object *ob;
+ struct direntry* file;
+
+ /* only when F4 DATABROWSE */
+ if(imasel_has_func(simasel)) return;
- case ESCKEY:
- filesel_prevspace();
- break;
-
- case PADENTER:
- case RETKEY:
- if (simasel->returnfunc){
- strcpy(name, simasel->dir);
- strcat(name, simasel->file);
- filesel_prevspace();
- simasel->returnfunc(name);
+ if( strcmp(simasel->dir, "Object/")==0 ) {
+ int n = BIF_filelist_numfiles(simasel->files);
+ if(simasel->active_file >= 0 && simasel->active_file < n) {
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+ ob= (Object *)file->poin;
+
+ if(ob) {
+ set_active_object(ob);
+ if(BASACT && BASACT->object==ob) {
+ BASACT->flag |= SELECT;
+ file->flags |= ACTIVE;
+ allqueue(REDRAWVIEW3D, 0);
+ allqueue(REDRAWOOPS, 0);
+ scrarea_queue_winredraw(curarea);
+ }
+ }
}
- break;
}
+}
+
+
+
+void winqreadimaselspace(ScrArea *, void *, BWinEvent *);
+
+
+void winqreadimaselspace(ScrArea *sa, void *spacedata, BWinEvent *evt)
+{
+ unsigned short event= evt->event;
+ short val= evt->val;
+ SpaceImaSel *simasel;
+ char str[FILE_MAXDIR+FILE_MAXFILE+12];
+ short mval[2];
+ short do_draw = 0;
+ int numfiles;
+ struct direntry *file;
+ float scrollstep = 0;
+ float scrollarea;
+
+ // if(val==0) return;
+ simasel= curarea->spacedata.first;
+
+ if (!simasel->files)
+ return;
+
+ if (BIF_filelist_empty(simasel->files))
+ return;
+
+ numfiles = BIF_filelist_numfiles(simasel->files);
+
+ /* calc_scrollrcts(sa, &(simasel->v2d), sa->winx, sa->winy); */
+ calc_imasel_rcts(simasel, sa->winx, sa->winy);
+
+ /* prevent looping */
+ if(simasel->selstate && !(get_mbut() & R_MOUSE)) simasel->selstate= 0;
+
+ if(val) {
+
+ if( event!=RETKEY && event!=PADENTER)
+ if( uiDoBlocks(&curarea->uiblocks, event)!=UI_NOTHING ) event= 0;
+
+ switch(event) {
- if (queredraw) scrarea_queue_winredraw(curarea);
+ case UI_BUT_EVENT:
+ do_imasel_buttons(val, simasel);
+ break;
+ case RENDERPREVIEW:
+ do_draw= 1;
+ /* draw_imasel_previews(sa, simasel); */
+ break;
+ case REDRAWIMASEL:
+ do_draw= 1;
+ break;
+ case WHEELDOWNMOUSE:
+ numfiles = BIF_filelist_numfiles(simasel->files);
+ scrollarea = ((float)simasel->v2d.vert.ymax - (float)simasel->v2d.vert.ymin);
+ scrollstep = ((scrollarea-simasel->scrollheight)/numfiles)*simasel->numtilesx;
+ simasel->scrollpos += scrollstep;
+ if (simasel->scrollpos > scrollarea - simasel->scrollheight)
+ simasel->scrollpos = scrollarea - simasel->scrollheight;
+ do_draw= 1;
+ break;
+ case WHEELUPMOUSE:
+ numfiles = BIF_filelist_numfiles(simasel->files);
+ scrollarea = ((float)simasel->v2d.vert.ymax - (float)simasel->v2d.vert.ymin);
+ scrollstep = ((scrollarea-simasel->scrollheight)/numfiles)*simasel->numtilesx;
+ simasel->scrollpos -= scrollstep;
+ if (simasel->scrollpos<0)
+ simasel->scrollpos=0;
+ do_draw= 1;
+ break;
+ case PAGEUPKEY:
+ numfiles = BIF_filelist_numfiles(simasel->files);
+ scrollarea = ((float)simasel->v2d.vert.ymax - (float)simasel->v2d.vert.ymin);
+ scrollstep = ((scrollarea-simasel->scrollheight)/numfiles)
+ *simasel->numtilesx*simasel->numtilesy;
+ simasel->scrollpos -= scrollstep;
+ if (simasel->scrollpos<0)
+ simasel->scrollpos=0;
+ do_draw= 1;
+ break;
+ case PAGEDOWNKEY:
+ numfiles = BIF_filelist_numfiles(simasel->files);
+ scrollarea = ((float)simasel->v2d.vert.ymax - (float)simasel->v2d.vert.ymin);
+ scrollstep = ((scrollarea-simasel->scrollheight)/numfiles)
+ * simasel->numtilesx*simasel->numtilesy;
+ simasel->scrollpos += scrollstep;
+ if (simasel->scrollpos > scrollarea - simasel->scrollheight)
+ simasel->scrollpos = scrollarea - simasel->scrollheight;
+ do_draw= 1;
+ break;
+ case HOMEKEY:
+ simasel->scrollpos=0;
+ imasel_home(sa, simasel);
+ do_draw= 1;
+ break;
+ case ENDKEY:
+ simasel->scrollpos = simasel->scrollarea;
+ do_draw= 1;
+ break;
+
+ case ESCKEY:
+ BIF_filelist_free(simasel->files);
+ imasel_prevspace();
+ break;
+ case PERIODKEY:
+ BIF_filelist_free(simasel->files);
+ simasel->active_file = -1;
+ do_draw = 1;
+ break;
+ case LEFTMOUSE:
+ case MIDDLEMOUSE:
+ getmouseco_areawin(mval);
+ if(mval[0]>simasel->v2d.vert.xmin && mval[0]<simasel->v2d.vert.xmax && mval[1]>simasel->v2d.vert.ymin && mval[1]<simasel->v2d.vert.ymax) {
+ do_filescroll(simasel);
+ }
+ else if(mval[0]>simasel->viewrect.xmin && mval[0]<simasel->viewrect.xmax
+ && mval[1]>simasel->viewrect.ymin && mval[1]<simasel->viewrect.ymax) {
+ set_active_file(simasel, mval[0], mval[1]);
+ if (simasel->active_file >= 0 && simasel->active_file < numfiles) {
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+
+ if(file && S_ISDIR(file->type)) {
+
+ BIF_filelist_appenddir(simasel->files, file->relname);
+ BLI_strncpy(simasel->dir, BIF_filelist_dir(simasel->files), FILE_MAXDIR);
+ strcat(simasel->dir,"/");
+ simasel->file[0] = '\0';
+ BLI_cleanup_dir(G.sce, simasel->dir);
+ BIF_filelist_free(simasel->files);
+ simasel->active_file = -1;
+ simasel->scrollpos = 0;
+ do_draw = 1;
+
+ }
+ else if (file)
+ {
+ if (file->relname) {
+ if (simasel->img) {
+ IMB_freeImBuf(simasel->img);
+ simasel->img = NULL;
+ }
+ BLI_strncpy(simasel->file, file->relname, FILE_MAXFILE);
+ if(event==MIDDLEMOUSE && BIF_filelist_gettype(simasel->files))
+ imasel_execute(simasel);
+ }
+
+ }
+ if(BIF_filelist_gettype(simasel->files)==FILE_MAIN) {
+ active_imasel_object(simasel);
+ }
+
+ do_draw = 1;
+ }
+ }
+ else {
+ simasel->active_file = -1;
+ if (simasel->flag & FILE_BOOKMARKS) {
+ if(mval[0]>simasel->bookmarkrect.xmin && mval[0]<simasel->bookmarkrect.xmax && mval[1]>simasel->bookmarkrect.ymin && mval[1]<simasel->bookmarkrect.ymax) {
+ int nentries = fsmenu_get_nentries();
+
+ set_active_bookmark(simasel, mval[1]);
+ if (simasel->active_bookmark >= 0 && simasel->active_bookmark < nentries) {
+ char *selected= fsmenu_get_entry(simasel->active_bookmark);
+ /* which string */
+ if (selected) {
+ BLI_strncpy(simasel->dir, selected, sizeof(simasel->dir));
+ BLI_make_exist(simasel->dir);
+ BLI_cleanup_dir(G.sce, simasel->dir);
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ simasel->file[0] = '\0';
+ simasel->scrollpos = 0;
+ simasel->active_file = -1;
+ scrarea_queue_winredraw(curarea);
+ }
+ }
+ } else {
+ simasel->active_bookmark = -1;
+ }
+ do_draw= 1;
+ }
+ }
+ break;
+ case RIGHTMOUSE:
+ getmouseco_areawin(mval);
+ if(mval[0]>simasel->viewrect.xmin && mval[0]<simasel->viewrect.xmax
+ && mval[1]>simasel->viewrect.ymin && mval[1]<simasel->viewrect.ymax) {
+ set_active_file(simasel, mval[0], mval[1]);
+ if(simasel->active_file >=0 && simasel->active_file<numfiles) {
+ simasel->selstate = NOTACTIVE;
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+ if (file->flags & ACTIVE) {
+ file->flags &= ~ACTIVE;
+ simasel->selstate = INACTIVATE;
+ }
+ else {
+ file->flags |= ACTIVE;
+ simasel->selstate = ACTIVATE;
+ }
+ do_draw= 1;
+ }
+ }
+ break;
+ case MOUSEY:
+ case MOUSEX:
+ getmouseco_areawin(mval);
+ if(mval[0]>simasel->viewrect.xmin && mval[0]<simasel->viewrect.xmax && mval[1]>simasel->viewrect.ymin && mval[1]<simasel->viewrect.ymax) {
+ set_active_file(simasel, mval[0], mval[1]);
+ if(simasel->active_file >=0 && simasel->active_file<numfiles) {
+ file = BIF_filelist_file(simasel->files, simasel->active_file);
+ if (simasel->selstate == INACTIVATE) {
+ file->flags &= ~ACTIVE;
+ }
+ else if (simasel->selstate == ACTIVATE) {
+ file->flags |= ACTIVE;
+ }
+ do_draw= 1;
+ }
+ } else {
+ simasel->active_file = -1;
+ if (simasel->flag & FILE_BOOKMARKS) {
+ if(mval[0]>simasel->bookmarkrect.xmin && mval[0]<simasel->bookmarkrect.xmax && mval[1]>simasel->bookmarkrect.ymin && mval[1]<simasel->bookmarkrect.ymax) {
+ set_active_bookmark(simasel, mval[1]);
+ do_draw= 1;
+ } else {
+ simasel->active_bookmark = -1;
+ }
+ }
+ }
+ break;
+ case AKEY:
+ BIF_filelist_swapselect(simasel->files);
+ if(simasel->type==FILE_MAIN) imasel_select_objects(simasel);
+ do_draw= 1;
+ break;
+ case BKEY:
+ toggle_blockhandler(sa, IMASEL_HANDLER_IMAGE, UI_PNL_UNSTOW);
+ scrarea_queue_winredraw(sa);
+ break;
+ case PKEY:
+ if(G.qual & LR_SHIFTKEY) {
+ extern char bprogname[]; /* usiblender.c */
+
+ sprintf(str, "%s -a \"%s%s\"", bprogname, simasel->dir, simasel->file);
+ system(str);
+ }
+ else
+ {
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_parent(simasel->files);
+ BLI_strncpy(simasel->dir, BIF_filelist_dir(simasel->files), 80);
+ simasel->file[0] = '\0';
+ simasel->active_file = -1;
+ simasel->scrollpos = 0;
+ }
+ do_draw = 1;
+ break;
+ case XKEY:
+ getmouseco_areawin(mval);
+ if (simasel->flag & FILE_BOOKMARKS) {
+ if(mval[0]>simasel->bookmarkrect.xmin && mval[0]<simasel->bookmarkrect.xmax && mval[1]>simasel->bookmarkrect.ymin && mval[1]<simasel->bookmarkrect.ymax) {
+ int nentries = fsmenu_get_nentries();
+ set_active_bookmark(simasel, mval[1]);
+ if (simasel->active_bookmark >= 0 && simasel->active_bookmark < nentries) {
+ fsmenu_remove_entry(simasel->active_bookmark);
+ simasel->active_bookmark = -1;
+ do_draw = 1;
+ }
+ }
+ }
+ break;
+ }
+ }
+ else if(event==RIGHTMOUSE) {
+ simasel->selstate = NOTACTIVE;
+ if(simasel->type==FILE_MAIN) imasel_select_objects(simasel);
+ }
+ else if(event==LEFTMOUSE) {
+ if(simasel->type==FILE_MAIN) {
+ getmouseco_areawin(mval);
+ set_active_file(simasel, mval[0], mval[1]);
+ }
+ }
+ /* XXX, stupid patch, curarea can become undone
+ * because of file loading... fixme zr
+ */
+ if(do_draw && curarea) scrarea_queue_winredraw(curarea);
}
+/* copied from filesel.c */
void clever_numbuts_imasel()
{
SpaceImaSel *simasel;
- static char orgname[FILE_MAXDIR+FILE_MAXFILE+12];
- static char filename[FILE_MAXDIR+FILE_MAXFILE+12];
- static char newname[FILE_MAXDIR+FILE_MAXFILE+12];
+ char orgname[FILE_MAXDIR+FILE_MAXFILE+12];
+ char filename[FILE_MAXDIR+FILE_MAXFILE+12];
+ char newname[FILE_MAXDIR+FILE_MAXFILE+12];
+ struct direntry *file;
int len;
simasel= curarea->spacedata.first;
+
+ if(BIF_filelist_gettype(simasel->files)==FILE_MAIN) return;
+
len = 110;
+ file = get_hilited_entry(simasel);
+
+ if (file != NULL && !(S_ISDIR(file->type))){
+
+ BLI_make_file_string(G.sce, orgname, simasel->dir, file->relname);
+ BLI_strncpy(filename, file->relname, sizeof(filename));
- if (simasel->hilite_ima){
- BLI_make_file_string(G.sce, orgname, simasel->dir, simasel->hilite_ima->file_name);
- strcpy(filename, simasel->hilite_ima->file_name);
+ add_numbut(0, TEX, "", 0, len, filename, "Rename File");
- add_numbut(0, TEX, "", 0, len, filename, "Rename Image");
- if( do_clever_numbuts("Rename Image", 1, REDRAW) ) {
+ if( do_clever_numbuts("Rename File", 1, REDRAW) ) {
BLI_make_file_string(G.sce, newname, simasel->dir, filename);
if( strcmp(orgname, newname) != 0 ) {
BLI_rename(orgname, newname);
-
- clear_ima_dir(simasel);
+ BIF_filelist_free(simasel->files);
}
}
diff --git a/source/blender/src/editscreen.c b/source/blender/src/editscreen.c
index 814985cb165..44069beaf43 100644
--- a/source/blender/src/editscreen.c
+++ b/source/blender/src/editscreen.c
@@ -358,6 +358,11 @@ void areawinset(short win)
G.v2d= &snode->v2d;
}
break;
+ case SPACE_IMASEL:
+ {
+ SpaceImaSel *simasel= curarea->spacedata.first;
+ G.v2d= &simasel->v2d;
+ }
default:
break;
}
diff --git a/source/blender/src/editsima.c b/source/blender/src/editsima.c
index 94990b8a393..06593227dbf 100644
--- a/source/blender/src/editsima.c
+++ b/source/blender/src/editsima.c
@@ -79,6 +79,7 @@
#include "BIF_gl.h"
#include "BIF_glutil.h"
+#include "BIF_imasel.h"
#include "BIF_interface.h"
#include "BIF_drawimage.h"
#include "BIF_editview.h"
diff --git a/source/blender/src/filelist.c b/source/blender/src/filelist.c
new file mode 100644
index 00000000000..6dc97faca4e
--- /dev/null
+++ b/source/blender/src/filelist.c
@@ -0,0 +1,1093 @@
+/**
+ * $Id: $
+ *
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2007 Blender Foundation.
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): none yet.
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+
+/* global includes */
+
+#include <stdlib.h>
+#include <math.h>
+#include <string.h>
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#ifndef WIN32
+#include <unistd.h>
+#else
+#include <io.h>
+#include <direct.h>
+#endif
+#include "MEM_guardedalloc.h"
+
+#include "BLI_blenlib.h"
+#include "BLI_linklist.h"
+#include "BLI_storage_types.h"
+
+#ifdef WIN32
+#include "BLI_winstuff.h"
+#endif
+
+#include "BKE_utildefines.h"
+#include "BKE_global.h"
+#include "BIF_filelist.h"
+#include "BKE_library.h"
+#include "BKE_global.h"
+#include "BKE_main.h"
+#include "BLO_readfile.h"
+
+#include "DNA_space_types.h"
+#include "DNA_ipo_types.h"
+#include "DNA_ID.h"
+#include "DNA_object_types.h"
+#include "DNA_lamp_types.h"
+#include "DNA_material_types.h"
+#include "DNA_texture_types.h"
+#include "DNA_world_types.h"
+#include "DNA_scene_types.h"
+#include "DNA_userdef_types.h"
+
+#include "IMB_imbuf.h"
+#include "IMB_imbuf_types.h"
+#include "IMB_thumbs.h"
+
+#include "PIL_time.h"
+
+#include "datatoc.h"
+
+/* Elubie: VERY, really very ugly and evil! Remove asap!!! */
+/* for state of file */
+#define ACTIVE 2
+
+/* max length of library group name within filesel */
+#define GROUP_MAX 32
+
+typedef struct FileList
+{
+ struct direntry *filelist;
+ struct direntry *unfiltered;
+
+ int numfiles;
+ int numunfiltered;
+ char dir[FILE_MAXDIR];
+ short type;
+ short ipotype;
+ struct BlendHandle *libfiledata;
+ int has_func;
+ short prv_w;
+ short prv_h;
+ short hide_dot;
+ unsigned int filter;
+} FileList;
+
+int BIF_groupname_to_code(char *group)
+{
+ char buf[32];
+ char *lslash;
+
+ BLI_strncpy(buf, group, 31);
+ lslash= BLI_last_slash(buf);
+ if (lslash)
+ lslash[0]= '\0';
+
+ return BLO_idcode_from_name(buf);
+}
+
+
+#define SPECIAL_IMG_SIZE 48
+#define SPECIAL_IMG_ROWS 4
+#define SPECIAL_IMG_COLS 4
+
+#define SPECIAL_IMG_FOLDER 0
+#define SPECIAL_IMG_PARENT 1
+#define SPECIAL_IMG_REFRESH 2
+#define SPECIAL_IMG_BLENDFILE 3
+#define SPECIAL_IMG_SOUNDFILE 4
+#define SPECIAL_IMG_MOVIEFILE 5
+#define SPECIAL_IMG_PYTHONFILE 6
+#define SPECIAL_IMG_TEXTFILE 7
+#define SPECIAL_IMG_FONTFILE 8
+#define SPECIAL_IMG_UNKNOWNFILE 9
+#define SPECIAL_IMG_MAX SPECIAL_IMG_UNKNOWNFILE + 1
+
+static ImBuf* gSpecialFileImages[SPECIAL_IMG_MAX];
+
+
+/* ******************* SORT ******************* */
+
+static int compare_name(const void *a1, const void *a2)
+{
+ const struct direntry *entry1=a1, *entry2=a2;
+
+ /* type is is equal to stat.st_mode */
+
+ if (S_ISDIR(entry1->type)){
+ if (S_ISDIR(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISDIR(entry2->type)) return (1);
+ }
+ if (S_ISREG(entry1->type)){
+ if (S_ISREG(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISREG(entry2->type)) return (1);
+ }
+ if ((entry1->type & S_IFMT) < (entry2->type & S_IFMT)) return (-1);
+ if ((entry1->type & S_IFMT) > (entry2->type & S_IFMT)) return (1);
+
+ /* make sure "." and ".." are always first */
+ if( strcmp(entry1->relname, ".")==0 ) return (-1);
+ if( strcmp(entry2->relname, ".")==0 ) return (1);
+ if( strcmp(entry1->relname, "..")==0 ) return (-1);
+
+ return (BLI_strcasecmp(entry1->relname,entry2->relname));
+}
+
+static int compare_date(const void *a1, const void *a2)
+{
+ const struct direntry *entry1=a1, *entry2=a2;
+
+ /* type is equal to stat.st_mode */
+
+ if (S_ISDIR(entry1->type)){
+ if (S_ISDIR(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISDIR(entry2->type)) return (1);
+ }
+ if (S_ISREG(entry1->type)){
+ if (S_ISREG(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISREG(entry2->type)) return (1);
+ }
+ if ((entry1->type & S_IFMT) < (entry2->type & S_IFMT)) return (-1);
+ if ((entry1->type & S_IFMT) > (entry2->type & S_IFMT)) return (1);
+
+ /* make sure "." and ".." are always first */
+ if( strcmp(entry1->relname, ".")==0 ) return (-1);
+ if( strcmp(entry2->relname, ".")==0 ) return (1);
+ if( strcmp(entry1->relname, "..")==0 ) return (-1);
+
+ if ( entry1->s.st_mtime < entry2->s.st_mtime) return 1;
+ if ( entry1->s.st_mtime > entry2->s.st_mtime) return -1;
+
+ else return BLI_strcasecmp(entry1->relname,entry2->relname);
+}
+
+static int compare_size(const void *a1, const void *a2)
+{
+ const struct direntry *entry1=a1, *entry2=a2;
+
+ /* type is equal to stat.st_mode */
+
+ if (S_ISDIR(entry1->type)){
+ if (S_ISDIR(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISDIR(entry2->type)) return (1);
+ }
+ if (S_ISREG(entry1->type)){
+ if (S_ISREG(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISREG(entry2->type)) return (1);
+ }
+ if ((entry1->type & S_IFMT) < (entry2->type & S_IFMT)) return (-1);
+ if ((entry1->type & S_IFMT) > (entry2->type & S_IFMT)) return (1);
+
+ /* make sure "." and ".." are always first */
+ if( strcmp(entry1->relname, ".")==0 ) return (-1);
+ if( strcmp(entry2->relname, ".")==0 ) return (1);
+ if( strcmp(entry1->relname, "..")==0 ) return (-1);
+
+ if ( entry1->s.st_size < entry2->s.st_size) return 1;
+ if ( entry1->s.st_size > entry2->s.st_size) return -1;
+ else return BLI_strcasecmp(entry1->relname,entry2->relname);
+}
+
+static int compare_extension(const void *a1, const void *a2) {
+ const struct direntry *entry1=a1, *entry2=a2;
+ char *sufix1, *sufix2;
+ char *nil="";
+
+ if (!(sufix1= strstr (entry1->relname, ".blend.gz")))
+ sufix1= strrchr (entry1->relname, '.');
+ if (!(sufix2= strstr (entry2->relname, ".blend.gz")))
+ sufix2= strrchr (entry2->relname, '.');
+ if (!sufix1) sufix1= nil;
+ if (!sufix2) sufix2= nil;
+
+ /* type is is equal to stat.st_mode */
+
+ if (S_ISDIR(entry1->type)){
+ if (S_ISDIR(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISDIR(entry2->type)) return (1);
+ }
+ if (S_ISREG(entry1->type)){
+ if (S_ISREG(entry2->type)==0) return (-1);
+ } else{
+ if (S_ISREG(entry2->type)) return (1);
+ }
+ if ((entry1->type & S_IFMT) < (entry2->type & S_IFMT)) return (-1);
+ if ((entry1->type & S_IFMT) > (entry2->type & S_IFMT)) return (1);
+
+ /* make sure "." and ".." are always first */
+ if( strcmp(entry1->relname, ".")==0 ) return (-1);
+ if( strcmp(entry2->relname, ".")==0 ) return (1);
+ if( strcmp(entry1->relname, "..")==0 ) return (-1);
+ if( strcmp(entry2->relname, "..")==0 ) return (-1);
+
+ return (BLI_strcasecmp(sufix1, sufix2));
+}
+
+void BIF_filelist_filter(FileList* filelist)
+{
+ int num_files = 0;
+ int num_filtered = 0;
+ struct direntry *old_filelist;
+ int i, j;
+
+ if (!filelist->filelist)
+ return;
+
+ if (!filelist->filter) {
+ if (filelist->unfiltered) {
+ old_filelist = filelist->filelist;
+ filelist->filelist = filelist->unfiltered;
+ filelist->numfiles = filelist->numunfiltered;
+ filelist->unfiltered = 0;
+ filelist->numunfiltered = 0;
+ free (old_filelist);
+ }
+ return;
+ }
+
+ if (!filelist->unfiltered) {
+ filelist->unfiltered = filelist->filelist;
+ filelist->numunfiltered = filelist->numfiles;
+ }
+
+ old_filelist = filelist->unfiltered;
+ num_files = filelist->numunfiltered;
+
+ filelist->filelist = 0;
+
+ // How many files are left after filter ?
+ for (i = 0; i < num_files; ++i) {
+ if (old_filelist[i].flags & filelist->filter) {
+ num_filtered++;
+ }
+ else if (old_filelist[i].type & S_IFDIR) {
+ if (filelist->filter & FOLDERFILE) {
+ num_filtered++;
+ }
+ }
+ }
+
+ filelist->filelist = (struct direntry *)malloc(num_filtered * sizeof(struct direntry));
+ filelist->numfiles = num_filtered;
+
+ for (i = 0, j=0; i < num_files; ++i) {
+ if (old_filelist[i].flags & filelist->filter) {
+ filelist->filelist[j++] = old_filelist[i];
+ }
+ else if (old_filelist[i].type & S_IFDIR) {
+ if (filelist->filter & FOLDERFILE) {
+ filelist->filelist[j++] = old_filelist[i];
+ }
+ }
+ }
+}
+
+void BIF_filelist_init_icons()
+{
+ short x, y, k;
+ ImBuf *bbuf;
+ ImBuf *ibuf;
+ bbuf = IMB_ibImageFromMemory((int *)datatoc_prvicons, datatoc_prvicons_size, IB_rect);
+ if (bbuf) {
+ for (y=0; y<SPECIAL_IMG_ROWS; y++) {
+ for (x=0; x<SPECIAL_IMG_COLS; x++) {
+ int tile = SPECIAL_IMG_COLS*y + x;
+ if (tile < SPECIAL_IMG_MAX) {
+ ibuf = IMB_allocImBuf(SPECIAL_IMG_SIZE, SPECIAL_IMG_SIZE, 32, IB_rect, 0);
+ for (k=0; k<SPECIAL_IMG_SIZE; k++) {
+ memcpy(&ibuf->rect[k*SPECIAL_IMG_SIZE], &bbuf->rect[(k+y*SPECIAL_IMG_SIZE)*SPECIAL_IMG_SIZE*SPECIAL_IMG_COLS+x*SPECIAL_IMG_SIZE], SPECIAL_IMG_SIZE*sizeof(int));
+ }
+ gSpecialFileImages[tile] = ibuf;
+ }
+ }
+ }
+ IMB_freeImBuf(bbuf);
+ }
+
+}
+
+void BIF_filelist_free_icons()
+{
+ int i;
+ for (i=0; i < SPECIAL_IMG_MAX; ++i) {
+ IMB_freeImBuf(gSpecialFileImages[i]);
+ gSpecialFileImages[i] = NULL;
+ }
+}
+
+struct FileList* BIF_filelist_new()
+{
+ FileList* p = MEM_callocN( sizeof(FileList), "filelist" );
+ p->filelist = 0;
+ p->numfiles = 0;
+ p->dir[0] = '\0';
+ p->libfiledata = 0;
+ p->type = 0;
+ p->has_func = 0;
+ p->filter = 0;
+ return p;
+}
+
+struct FileList* BIF_filelist_copy(struct FileList* filelist)
+{
+ FileList* p = BIF_filelist_new();
+ BLI_strncpy(p->dir, filelist->dir, FILE_MAXDIR);
+ p->filelist = NULL;
+ p->unfiltered = NULL;
+ p->type = filelist->type;
+ p->ipotype = filelist->ipotype;
+ p->has_func = filelist->has_func;
+
+ return p;
+}
+
+void BIF_filelist_free(struct FileList* filelist)
+{
+ int i;
+
+ if (!filelist) {
+ printf("Attemtping to delete empty filelist.\n");
+ return;
+ }
+
+ if (filelist->unfiltered) {
+ struct direntry* filtered_files = filelist->filelist;
+ filelist->filelist = filelist->unfiltered;
+ filelist->numfiles = filelist->numunfiltered;
+ filelist->numunfiltered = 0;
+ free (filtered_files);
+ filelist->unfiltered = 0;
+ }
+
+ for (i = 0; i < filelist->numfiles; ++i) {
+ if (filelist->filelist[i].image)
+ IMB_freeImBuf(filelist->filelist[i].image);
+ filelist->filelist[i].image = 0;
+ if (filelist->filelist[i].relname)
+ MEM_freeN(filelist->filelist[i].relname);
+ filelist->filelist[i].relname = 0;
+ if (filelist->filelist[i].string)
+ MEM_freeN(filelist->filelist[i].string);
+ filelist->filelist[i].string = 0;
+ }
+
+ filelist->numfiles = 0;
+ free(filelist->filelist);
+ filelist->filelist = 0;
+}
+
+void BIF_filelist_freelib(struct FileList* filelist)
+{
+ if(filelist->libfiledata)
+ BLO_blendhandle_close(filelist->libfiledata);
+ filelist->libfiledata= 0;
+}
+
+struct BlendHandle *BIF_filelist_lib(struct FileList* filelist)
+{
+ return filelist->libfiledata;
+}
+
+int BIF_filelist_numfiles(struct FileList* filelist)
+{
+ return filelist->numfiles;
+}
+
+const char * BIF_filelist_dir(struct FileList* filelist)
+{
+ return filelist->dir;
+}
+
+void BIF_filelist_setdir(struct FileList* filelist, const char *dir)
+{
+ BLI_strncpy(filelist->dir, dir, FILE_MAXDIR);
+}
+
+void BIF_filelist_appenddir(struct FileList* filelist, const char *relname)
+{
+ strcat(filelist->dir, relname);
+ BLI_cleanup_dir(G.sce, filelist->dir);
+}
+
+void BIF_filelist_imgsize(struct FileList* filelist, short w, short h)
+{
+ filelist->prv_w = w;
+ filelist->prv_h = h;
+}
+
+void BIF_filelist_loadimage(struct FileList* filelist, int index)
+{
+ ImBuf *imb = NULL;
+ int imgwidth = filelist->prv_w;
+ int imgheight = filelist->prv_h;
+ short ex, ey, dx, dy;
+ float scaledx, scaledy;
+
+ if (!filelist->filelist[index].image)
+ {
+ if (filelist->type != FILE_MAIN)
+ {
+ if ( filelist->filelist[index].flags & IMAGEFILE ) {
+ imb = IMB_thumb_manage(filelist->dir, filelist->filelist[index].relname, THB_NORMAL, THB_SOURCE_IMAGE);
+ } else if ( filelist->filelist[index].flags & MOVIEFILE ) {
+ imb = IMB_thumb_manage(filelist->dir, filelist->filelist[index].relname, THB_NORMAL, THB_SOURCE_MOVIE);
+ if (!imb) {
+ /* remember that file can't be loaded via IMB_open_anim */
+ filelist->filelist[index].flags &= ~MOVIEFILE;
+ filelist->filelist[index].flags |= MOVIEFILE_ICON;
+ }
+ }
+ if (imb) {
+ if (imb->x > imb->y) {
+ scaledx = (float)imgwidth;
+ scaledy = ( (float)imb->y/(float)imb->x )*imgwidth;
+ }
+ else {
+ scaledy = imgheight;
+ scaledx = ( (float)imb->x/(float)imb->y )*imgheight;
+ }
+ ex = (short)scaledx;
+ ey = (short)scaledy;
+
+ dx = imgwidth - ex;
+ dy = imgheight - ey;
+
+ IMB_scaleImBuf(imb, ex, ey);
+
+ }
+ filelist->filelist[index].image = imb;
+
+ }
+ }
+}
+
+struct ImBuf * BIF_filelist_getimage(struct FileList* filelist, int index)
+{
+ ImBuf* ibuf = filelist->filelist[index].image;
+ if (ibuf == NULL) {
+ struct direntry *file = &filelist->filelist[index];
+ if (file->type & S_IFDIR) {
+ if ( strcmp(filelist->filelist[index].relname, "..") == 0) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_PARENT];
+ } else if ( strcmp(filelist->filelist[index].relname, ".") == 0) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_REFRESH];
+ } else {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_FOLDER];
+ }
+ } else {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_UNKNOWNFILE];
+ }
+
+ if (file->flags & BLENDERFILE) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_BLENDFILE];
+ } else if ( (file->flags & MOVIEFILE) || (file->flags & MOVIEFILE_ICON) ) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_MOVIEFILE];
+ } else if (file->flags & SOUNDFILE) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_SOUNDFILE];
+ } else if (file->flags & PYSCRIPTFILE) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_PYTHONFILE];
+ } else if (file->flags & FTFONTFILE) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_FONTFILE];
+ } else if (file->flags & TEXTFILE) {
+ ibuf = gSpecialFileImages[SPECIAL_IMG_TEXTFILE];
+ }
+ }
+ return ibuf;
+}
+
+struct direntry * BIF_filelist_file(struct FileList* filelist, int index)
+{
+ return &filelist->filelist[index];
+}
+
+int BIF_filelist_find(struct FileList* filelist, char *file)
+{
+ int index = -1;
+ int i;
+
+ for (i = 0; i < filelist->numfiles; ++i) {
+ if ( strcmp(filelist->filelist[i].relname, file) == 0) {
+ index = i;
+ break;
+ }
+ }
+ return index;
+}
+
+void BIF_filelist_hidedot(struct FileList* filelist, short hide)
+{
+ filelist->hide_dot = hide;
+}
+
+void BIF_filelist_setfilter(struct FileList* filelist, unsigned int filter)
+{
+ filelist->filter = filter;
+}
+
+void BIF_filelist_readdir(struct FileList* filelist)
+{
+ char wdir[FILE_MAXDIR];
+ int finished = 0;
+
+ if (!filelist) return;
+ filelist->unfiltered = 0;
+ filelist->filelist = 0;
+
+ if(filelist->type==FILE_MAIN) {
+ BIF_filelist_from_main(filelist);
+ finished = 1;
+ } else if(filelist->type==FILE_LOADLIB) {
+ BLI_cleanup_dir(G.sce, filelist->dir);
+ BIF_filelist_from_library(filelist);
+ if(filelist->libfiledata) {
+ finished = 1;
+ }
+ }
+
+ if (!finished) {
+ BLI_getwdN(wdir);
+
+ BLI_cleanup_dir(G.sce, filelist->dir);
+ BLI_hide_dot_files(filelist->hide_dot);
+ filelist->numfiles = BLI_getdir(filelist->dir, &(filelist->filelist));
+
+ chdir(wdir);
+ BIF_filelist_setfiletypes(filelist, G.have_quicktime);
+ BIF_filelist_filter(filelist);
+
+ }
+}
+
+int BIF_filelist_empty(struct FileList* filelist)
+{
+ return filelist->filelist == 0;
+}
+
+void BIF_filelist_parent(struct FileList* filelist)
+{
+#ifdef WIN32
+ char c = '\\';
+#else
+ char c = '/';
+#endif
+ char *dir = filelist->dir;
+ size_t len = strlen(dir);
+
+ while( (len > 0) && (dir[len-1] == c) )
+ {
+ --len;
+ dir[len] = '\0';
+ }
+ while ( (len > 0) && (dir[len-1] != c) )
+ {
+ --len;
+ dir[len] = '\0';
+ }
+ if (len == 0)
+ {
+ dir[0] = c; dir[1] = '\0';
+ }
+#ifdef WIN32
+ strcat(filelist->dir, "\\");
+#else
+ strcat(filelist->dir, "/");
+#endif
+
+ BLI_cleanup_dir(G.sce, filelist->dir);
+ BLI_make_exist(filelist->dir);
+ BIF_filelist_readdir(filelist);
+}
+
+void BIF_filelist_setfiletypes(struct FileList* filelist, short has_quicktime)
+{
+ struct direntry *file;
+ int num;
+
+ file= filelist->filelist;
+
+ for(num=0; num<filelist->numfiles; num++, file++) {
+ file->flags= 0;
+ file->type= file->s.st_mode; /* restore the mess below */
+
+ /* Don't check extensions for directories */
+ if (file->type & S_IFDIR)
+ continue;
+
+
+
+ if(BLO_has_bfile_extension(file->relname)) {
+ file->flags |= BLENDERFILE;
+ if(filelist->type==FILE_LOADLIB) {
+ char name[FILE_MAXDIR+FILE_MAXFILE];
+ BLI_strncpy(name, filelist->dir, sizeof(name));
+ strcat(name, file->relname);
+
+ /* prevent current file being used as acceptable dir */
+ if (BLI_streq(G.main->name, name)==0) {
+ file->type &= ~S_IFMT;
+ file->type |= S_IFDIR;
+ }
+ }
+ } else if(BLI_testextensie(file->relname, ".py")) {
+ file->flags |= PYSCRIPTFILE;
+ } else if(BLI_testextensie(file->relname, ".txt")) {
+ file->flags |= TEXTFILE;
+ } else if( BLI_testextensie(file->relname, ".ttf")
+ || BLI_testextensie(file->relname, ".ttc")
+ || BLI_testextensie(file->relname, ".pfb")
+ || BLI_testextensie(file->relname, ".otf")
+ || BLI_testextensie(file->relname, ".otc")) {
+ file->flags |= FTFONTFILE;
+ } else if (has_quicktime){
+ if( BLI_testextensie(file->relname, ".jpg")
+ || BLI_testextensie(file->relname, ".jpeg")
+ || BLI_testextensie(file->relname, ".tga")
+ || BLI_testextensie(file->relname, ".rgb")
+ || BLI_testextensie(file->relname, ".bmp")
+ || BLI_testextensie(file->relname, ".png")
+ || BLI_testextensie(file->relname, ".iff")
+ || BLI_testextensie(file->relname, ".lbm")
+ || BLI_testextensie(file->relname, ".gif")
+ || BLI_testextensie(file->relname, ".psd")
+ || BLI_testextensie(file->relname, ".tif")
+ || BLI_testextensie(file->relname, ".tiff")
+ || BLI_testextensie(file->relname, ".pct")
+ || BLI_testextensie(file->relname, ".pict")
+ || BLI_testextensie(file->relname, ".pntg") //macpaint
+ || BLI_testextensie(file->relname, ".qtif")
+ || BLI_testextensie(file->relname, ".sgi")
+#ifdef WITH_OPENEXR
+ || BLI_testextensie(file->relname, ".exr")
+#endif
+ ) {
+ file->flags |= IMAGEFILE;
+ }
+ else if(BLI_testextensie(file->relname, ".avi")
+ || BLI_testextensie(file->relname, ".flc")
+ || BLI_testextensie(file->relname, ".mov")
+ || BLI_testextensie(file->relname, ".movie")
+ || BLI_testextensie(file->relname, ".mp4")
+ || BLI_testextensie(file->relname, ".m4v")
+ || BLI_testextensie(file->relname, ".mv")) {
+ file->flags |= MOVIEFILE;
+ }
+ else if(BLI_testextensie(file->relname, ".wav")) {
+ file->flags |= SOUNDFILE;
+ }
+ } else { // no quicktime
+ if(BLI_testextensie(file->relname, ".jpg")
+ || BLI_testextensie(file->relname, ".tga")
+ || BLI_testextensie(file->relname, ".rgb")
+ || BLI_testextensie(file->relname, ".bmp")
+ || BLI_testextensie(file->relname, ".png")
+ || BLI_testextensie(file->relname, ".iff")
+ || BLI_testextensie(file->relname, ".tif")
+ || BLI_testextensie(file->relname, ".tiff")
+#ifdef WITH_OPENEXR
+ || BLI_testextensie(file->relname, ".exr")
+#endif
+ || BLI_testextensie(file->relname, ".lbm")
+ || BLI_testextensie(file->relname, ".sgi")) {
+ file->flags |= IMAGEFILE;
+ }
+ else if(BLI_testextensie(file->relname, ".avi")
+ || BLI_testextensie(file->relname, ".mp4")
+ || BLI_testextensie(file->relname, ".mv")) {
+ file->flags |= MOVIEFILE;
+ }
+ else if(BLI_testextensie(file->relname, ".wav")) {
+ file->flags |= SOUNDFILE;
+ }
+ }
+ }
+}
+
+void BIF_filelist_swapselect(struct FileList* filelist)
+{
+ struct direntry *file;
+ int num, act= 0;
+
+ file= filelist->filelist;
+ for(num=0; num<filelist->numfiles; num++, file++) {
+ if(file->flags & ACTIVE) {
+ act= 1;
+ break;
+ }
+ }
+ file= filelist->filelist+2;
+ for(num=2; num<filelist->numfiles; num++, file++) {
+ if(act) file->flags &= ~ACTIVE;
+ else file->flags |= ACTIVE;
+ }
+}
+
+int BIF_filelist_islibrary(struct FileList* filelist, char* dir, char* group)
+{
+ /* return ok when a blenderfile, in dir is the filename,
+ * in group the type of libdata
+ */
+ int len;
+ char *fd;
+
+ strcpy(dir, filelist->dir);
+ len= strlen(dir);
+ if(len<7) return 0;
+ if( dir[len-1] != '/' && dir[len-1] != '\\') return 0;
+
+ group[0]= 0;
+ dir[len-1]= 0;
+
+ /* Find the last slash */
+ fd= (strrchr(dir, '/')>strrchr(dir, '\\'))?strrchr(dir, '/'):strrchr(dir, '\\');
+
+ if(fd==0) return 0;
+ *fd= 0;
+ if(BLO_has_bfile_extension(fd+1)) {
+ *fd= '/';
+ }
+ else {
+ char *gp = fd+1; // in case we have a .blend file, gp points to the group
+
+ /* Find the last slash */
+ fd= (strrchr(dir, '/')>strrchr(dir, '\\'))?strrchr(dir, '/'):strrchr(dir, '\\');
+ if (!fd || !BLO_has_bfile_extension(fd+1)) return 0;
+
+ /* now we know that we are in a blend file and it is safe to
+ assume that gp actually points to a group */
+ BLI_strncpy(group, gp, GROUP_MAX);
+ }
+ return 1;
+}
+
+void BIF_filelist_from_library(struct FileList* filelist)
+{
+ LinkNode *l, *names, *previews;
+ struct ImBuf* ima;
+ int ok, i, nnames, idcode;
+ char filename[FILE_MAXDIR+FILE_MAXFILE];
+ char dir[FILE_MAXDIR], group[GROUP_MAX];
+
+ filelist->type = FILE_LOADLIB;
+
+ /* name test */
+ ok= BIF_filelist_islibrary(filelist, dir, group);
+ if (!ok) {
+ /* free */
+ if(filelist->libfiledata) BLO_blendhandle_close(filelist->libfiledata);
+ filelist->libfiledata= 0;
+ return;
+ }
+
+ BLI_strncpy(filename, G.sce, sizeof(filename)); // G.sce = last file loaded, for UI
+
+ /* there we go */
+ /* for the time being only read filedata when libfiledata==0 */
+ if (filelist->libfiledata==0) {
+ filelist->libfiledata= BLO_blendhandle_from_file(dir);
+ if(filelist->libfiledata==0) return;
+ }
+
+ idcode= BIF_groupname_to_code(group);
+
+ // memory for strings is passed into filelist[i].relname
+ // and free'd in freefilelist
+ previews = NULL;
+ if (idcode) {
+ previews= BLO_blendhandle_get_previews(filelist->libfiledata, idcode);
+ names= BLO_blendhandle_get_datablock_names(filelist->libfiledata, idcode);
+ /* ugh, no rewind, need to reopen */
+ BLO_blendhandle_close(filelist->libfiledata);
+ filelist->libfiledata= BLO_blendhandle_from_file(dir);
+
+ } else {
+ names= BLO_blendhandle_get_linkable_groups(filelist->libfiledata);
+ }
+
+ nnames= BLI_linklist_length(names);
+
+ filelist->numfiles= nnames + 2;
+ filelist->filelist= malloc(filelist->numfiles * sizeof(*filelist->filelist));
+ memset(filelist->filelist, 0, filelist->numfiles * sizeof(*filelist->filelist));
+
+ filelist->filelist[0].relname= BLI_strdup(".");
+ filelist->filelist[0].type |= S_IFDIR;
+ filelist->filelist[1].relname= BLI_strdup("..");
+ filelist->filelist[1].type |= S_IFDIR;
+
+ for (i=0, l= names; i<nnames; i++, l= l->next) {
+ char *blockname= l->link;
+
+ filelist->filelist[i + 2].relname= BLI_strdup(blockname);
+ if (!idcode)
+ filelist->filelist[i + 2].type |= S_IFDIR;
+ }
+
+ if(previews) {
+ for (i=0, l= previews; i<nnames; i++, l= l->next) {
+ PreviewImage *img= l->link;
+
+ if (img) {
+ unsigned int w = img->w[PREVIEW_MIPMAP_LARGE];
+ unsigned int h = img->h[PREVIEW_MIPMAP_LARGE];
+ unsigned int *rect = img->rect[PREVIEW_MIPMAP_LARGE];
+
+ /* first allocate imbuf for copying preview into it */
+ if (w > 0 && h > 0 && rect) {
+ ima = IMB_allocImBuf(w, h, 32, IB_rect, 0);
+ memcpy(ima->rect, rect, w*h*sizeof(unsigned int));
+ filelist->filelist[i + 2].image = ima;
+ filelist->filelist[i + 2].flags = IMAGEFILE;
+ }
+ }
+ }
+ }
+
+ BLI_linklist_free(names, free);
+ if (previews) BLI_linklist_free(previews, MEM_freeN);
+
+ BIF_filelist_sort(filelist, FILE_SORTALPHA);
+
+ BLI_strncpy(G.sce, filename, sizeof(filename)); // prevent G.sce to change
+}
+
+void BIF_filelist_append_library(struct FileList *filelist, char *dir, char *file, short flag, int idcode)
+{
+ BLO_library_append_(&filelist->libfiledata, filelist->filelist, filelist->numfiles, dir, file, flag, idcode);
+}
+
+void BIF_filelist_from_main(struct FileList *filelist)
+{
+ ID *id;
+ struct direntry *files, *firstlib = NULL;
+ ListBase *lb;
+ int a, fake, idcode, ok, totlib, totbl;
+
+ filelist->type = FILE_MAIN;
+
+ if(filelist->dir[0]=='/') filelist->dir[0]= 0;
+
+ if(filelist->dir[0]) {
+ idcode= BIF_groupname_to_code(filelist->dir);
+ if(idcode==0) filelist->dir[0]= 0;
+ }
+
+ if( filelist->dir[0]==0) {
+
+ /* make directories */
+ filelist->numfiles= 23;
+ filelist->filelist= (struct direntry *)malloc(filelist->numfiles * sizeof(struct direntry));
+
+ for(a=0; a<filelist->numfiles; a++) {
+ memset( &(filelist->filelist[a]), 0 , sizeof(struct direntry));
+ filelist->filelist[a].type |= S_IFDIR;
+ }
+
+ filelist->filelist[0].relname= BLI_strdup("..");
+ filelist->filelist[1].relname= BLI_strdup(".");
+ filelist->filelist[2].relname= BLI_strdup("Scene");
+ filelist->filelist[3].relname= BLI_strdup("Object");
+ filelist->filelist[4].relname= BLI_strdup("Mesh");
+ filelist->filelist[5].relname= BLI_strdup("Curve");
+ filelist->filelist[6].relname= BLI_strdup("Metaball");
+ filelist->filelist[7].relname= BLI_strdup("Material");
+ filelist->filelist[8].relname= BLI_strdup("Texture");
+ filelist->filelist[9].relname= BLI_strdup("Image");
+ filelist->filelist[10].relname= BLI_strdup("Ika");
+ filelist->filelist[11].relname= BLI_strdup("Wave");
+ filelist->filelist[12].relname= BLI_strdup("Lattice");
+ filelist->filelist[13].relname= BLI_strdup("Lamp");
+ filelist->filelist[14].relname= BLI_strdup("Camera");
+ filelist->filelist[15].relname= BLI_strdup("Ipo");
+ filelist->filelist[16].relname= BLI_strdup("World");
+ filelist->filelist[17].relname= BLI_strdup("Screen");
+ filelist->filelist[18].relname= BLI_strdup("VFont");
+ filelist->filelist[19].relname= BLI_strdup("Text");
+ filelist->filelist[20].relname= BLI_strdup("Armature");
+ filelist->filelist[21].relname= BLI_strdup("Action");
+ filelist->filelist[22].relname= BLI_strdup("NodeTree");
+ BIF_filelist_sort(filelist, FILE_SORTALPHA);
+ }
+ else {
+
+ /* make files */
+ idcode= BIF_groupname_to_code(filelist->dir);
+
+ lb= wich_libbase(G.main, idcode );
+ if(lb==0) return;
+
+ id= lb->first;
+ filelist->numfiles= 0;
+ while(id) {
+
+ if(filelist->has_func && idcode==ID_IP) {
+ if(filelist->ipotype== ((Ipo *)id)->blocktype) filelist->numfiles++;
+ }
+ else if (!filelist->hide_dot || id->name[2] != '.') {
+ filelist->numfiles++;
+ }
+
+ id= id->next;
+ }
+
+ if(!filelist->has_func) filelist->numfiles+= 2;
+ filelist->filelist= (struct direntry *)malloc(filelist->numfiles * sizeof(struct direntry));
+
+ files = filelist->filelist;
+
+ if(!filelist->has_func) {
+ memset( &(filelist->filelist[0]), 0 , sizeof(struct direntry));
+ filelist->filelist[0].relname= BLI_strdup(".");
+ filelist->filelist[0].type |= S_IFDIR;
+ memset( &(filelist->filelist[1]), 0 , sizeof(struct direntry));
+ filelist->filelist[1].relname= BLI_strdup("..");
+ filelist->filelist[1].type |= S_IFDIR;
+
+ files+= 2;
+ }
+
+ id= lb->first;
+ totlib= totbl= 0;
+
+ while(id) {
+
+ ok= 0;
+ if(filelist->has_func && idcode==ID_IP) {
+ if(filelist->ipotype== ((Ipo *)id)->blocktype) ok= 1;
+ }
+ else ok= 1;
+
+ if(ok) {
+ /* TODO: hide dot files - elubie */
+ memset( files, 0 , sizeof(struct direntry));
+ if(id->lib==NULL)
+ files->relname= BLI_strdup(id->name+2);
+ else {
+ files->relname= MEM_mallocN(FILE_MAXDIR+FILE_MAXFILE+32, "filename for lib");
+ sprintf(files->relname, "%s | %s", id->lib->name, id->name+2);
+ }
+ /* files->type |= S_IFDIR; */
+ if(!filelist->has_func) { /* F4 DATA BROWSE */
+ if(idcode==ID_OB) {
+ if( ((Object *)id)->flag & SELECT) files->flags |= ACTIVE;
+ }
+ else if(idcode==ID_SCE) {
+ if( ((Scene *)id)->r.scemode & R_BG_RENDER) files->flags |= ACTIVE;
+ }
+ }
+ files->nr= totbl+1;
+ files->poin= id;
+ fake= id->flag & LIB_FAKEUSER;
+ if(idcode == ID_MA || idcode == ID_TE || idcode == ID_LA || idcode == ID_WO || idcode == ID_IM) {
+ files->flags |= IMAGEFILE;
+ }
+ if(id->lib && fake) sprintf(files->extra, "LF %d", id->us);
+ else if(id->lib) sprintf(files->extra, "L %d", id->us);
+ else if(fake) sprintf(files->extra, "F %d", id->us);
+ else sprintf(files->extra, " %d", id->us);
+
+ if(id->lib) {
+ if(totlib==0) firstlib= files;
+ totlib++;
+ }
+
+ files++;
+ totbl++;
+ }
+
+ id= id->next;
+ }
+
+ /* only qsort of library blocks */
+ if(totlib>1) {
+ qsort(firstlib, totlib, sizeof(struct direntry), compare_name);
+ }
+ }
+}
+
+
+void BIF_filelist_settype(struct FileList* filelist, int type)
+{
+ filelist->type = type;
+}
+
+short BIF_filelist_gettype(struct FileList* filelist)
+{
+ return filelist->type;
+}
+
+void BIF_filelist_sort(struct FileList* filelist, short sort)
+{
+ struct direntry *file;
+ int num;/* , act= 0; */
+
+ switch(sort) {
+ case FILE_SORTALPHA:
+ qsort(filelist->filelist, filelist->numfiles, sizeof(struct direntry), compare_name);
+ break;
+ case FILE_SORTDATE:
+ qsort(filelist->filelist, filelist->numfiles, sizeof(struct direntry), compare_date);
+ break;
+ case FILE_SORTSIZE:
+ qsort(filelist->filelist, filelist->numfiles, sizeof(struct direntry), compare_size);
+ break;
+ case FILE_SORTEXTENS:
+ qsort(filelist->filelist, filelist->numfiles, sizeof(struct direntry), compare_extension);
+ }
+
+ file= filelist->filelist;
+ for(num=0; num<filelist->numfiles; num++, file++) {
+ file->flags &= ~HILITE;
+ }
+}
+
+
+void BIF_filelist_setipotype(struct FileList* filelist, short ipotype)
+{
+ filelist->ipotype = ipotype;
+}
+
+void BIF_filelist_hasfunc(struct FileList* filelist, int has_func)
+{
+ filelist->has_func = has_func;
+}
+
diff --git a/source/blender/src/filesel.c b/source/blender/src/filesel.c
index 036e13f3f3b..242c7c0a12c 100644
--- a/source/blender/src/filesel.c
+++ b/source/blender/src/filesel.c
@@ -86,6 +86,7 @@
#include "BKE_utildefines.h"
#include "BIF_editview.h"
+#include "BIF_filelist.h"
#include "BIF_gl.h"
#include "BIF_interface.h"
#include "BIF_language.h"
@@ -116,7 +117,7 @@
#endif
#if defined WIN32 || defined __BeOS
-int fnmatch(const char *pattern, const char *string, int flags)
+static int fnmatch(const char *pattern, const char *string, int flags)
{
return 0;
}
@@ -170,155 +171,6 @@ static float pixels_to_ofs;
static char otherdir[FILE_MAX];
static ScrArea *otherarea;
-/* FSMENU HANDLING */
-
- /* FSMenuEntry's without paths indicate seperators */
-typedef struct _FSMenuEntry FSMenuEntry;
-struct _FSMenuEntry {
- FSMenuEntry *next;
-
- char *path;
-};
-
-static FSMenuEntry *fsmenu= 0;
-
-int fsmenu_get_nentries(void)
-{
- FSMenuEntry *fsme;
- int count= 0;
-
- for (fsme= fsmenu; fsme; fsme= fsme->next)
- count++;
-
- return count;
-}
-int fsmenu_is_entry_a_seperator(int idx)
-{
- FSMenuEntry *fsme;
-
- for (fsme= fsmenu; fsme && idx; fsme= fsme->next)
- idx--;
-
- return (fsme && !fsme->path)?1:0;
-}
-char *fsmenu_get_entry(int idx)
-{
- FSMenuEntry *fsme;
-
- for (fsme= fsmenu; fsme && idx; fsme= fsme->next)
- idx--;
-
- return fsme?fsme->path:NULL;
-}
-char *fsmenu_build_menu(void)
-{
- DynStr *ds= BLI_dynstr_new();
- FSMenuEntry *fsme;
- char *menustr;
-
- for (fsme= fsmenu; fsme; fsme= fsme->next) {
- if (!fsme->path) {
- /* clean consecutive seperators and ignore trailing ones */
- if (fsme->next) {
- if (fsme->next->path) {
- BLI_dynstr_append(ds, "%l|");
- } else {
- FSMenuEntry *next= fsme->next;
- fsme->next= next->next;
- MEM_freeN(next);
- }
- }
- } else {
- BLI_dynstr_append(ds, fsme->path);
- if (fsme->next) BLI_dynstr_append(ds, "|");
- }
- }
-
- menustr= BLI_dynstr_get_cstring(ds);
- BLI_dynstr_free(ds);
- return menustr;
-}
-static FSMenuEntry *fsmenu_get_last_separator(void)
-{
- FSMenuEntry *fsme, *lsep=NULL;
-
- for (fsme= fsmenu; fsme; fsme= fsme->next)
- if (!fsme->path)
- lsep= fsme;
-
- return lsep;
-}
-void fsmenu_insert_entry(char *path, int sorted)
-{
- FSMenuEntry *prev= fsmenu_get_last_separator();
- FSMenuEntry *fsme= prev?prev->next:fsmenu;
-
- for (; fsme; prev= fsme, fsme= fsme->next) {
- if (fsme->path) {
- if (BLI_streq(path, fsme->path)) {
- return;
- } else if (sorted && strcmp(path, fsme->path)<0) {
- break;
- }
- }
- }
-
- fsme= MEM_mallocN(sizeof(*fsme), "fsme");
- fsme->path= BLI_strdup(path);
-
- if (prev) {
- fsme->next= prev->next;
- prev->next= fsme;
- } else {
- fsme->next= fsmenu;
- fsmenu= fsme;
- }
-}
-void fsmenu_append_seperator(void)
-{
- if (fsmenu) {
- FSMenuEntry *fsme= fsmenu;
-
- while (fsme->next) fsme= fsme->next;
-
- fsme->next= MEM_mallocN(sizeof(*fsme), "fsme");
- fsme->next->next= NULL;
- fsme->next->path= NULL;
- }
-}
-void fsmenu_remove_entry(int idx)
-{
- FSMenuEntry *prev= NULL, *fsme= fsmenu;
-
- for (fsme= fsmenu; fsme && idx; prev= fsme, fsme= fsme->next)
- if (fsme->path)
- idx--;
-
- if (fsme) {
- if (prev) {
- prev->next= fsme->next;
- } else {
- fsmenu= fsme->next;
- }
-
- MEM_freeN(fsme->path);
- MEM_freeN(fsme);
- }
-}
-void fsmenu_free(void)
-{
- FSMenuEntry *fsme= fsmenu;
-
- while (fsme) {
- FSMenuEntry *n= fsme->next;
-
- if (fsme->path) MEM_freeN(fsme->path);
- MEM_freeN(fsme);
-
- fsme= n;
- }
-}
-
/* ******************* SORT ******************* */
static int compare_name(const void *a1, const void *a2)
@@ -1399,41 +1251,6 @@ void activate_fileselect_args(int type, char *title, char *file, void (*func)(ch
activate_fileselect_(type, title, file, NULL, NULL, NULL, NULL, func, arg1, arg2);
}
-
-void activate_imageselect(int type, char *title, char *file, void (*func)(char *))
-{
- SpaceImaSel *simasel;
- char dir[FILE_MAX], name[FILE_MAX];
-
- if(curarea==NULL) return;
- if(curarea->win==0) return;
-
- newspace(curarea, SPACE_IMASEL);
-
- /* sometimes double, when area is already SPACE_FILE with a different file name */
- addqueue(curarea->headwin, CHANGED, 1);
- addqueue(curarea->win, CHANGED, 1);
-
- name[2]= 0;
- BLI_strncpy(name, file, sizeof(name));
-
- simasel= curarea->spacedata.first;
- simasel->returnfunc= func;
-
- if(BLI_convertstringcode(name, G.sce, G.scene->r.cfra)) simasel->mode |= IMS_STRINGCODE;
- else simasel->mode &= ~IMS_STRINGCODE;
-
- BLI_split_dirfile(name, dir, simasel->file);
- BLI_cleanup_dir(G.sce, simasel->dir);
- if(strcmp(dir, simasel->dir)!=0) simasel->fase= 0;
-
- BLI_strncpy(simasel->dir, dir, sizeof(simasel->dir));
- BLI_strncpy(simasel->title, title, sizeof(simasel->title));
-
- /* filetoname= 1; */
-}
-
-
void activate_databrowse(ID *id, int idcode, int fromcode, int retval, short *menup, void (*func)(unsigned short))
{
ListBase *lb;
@@ -1603,7 +1420,7 @@ static void filesel_execute(SpaceFile *sfile)
allqueue(REDRAWALL, 1);
}
else if(filesel_has_func(sfile)) {
- fsmenu_insert_entry(sfile->dir, 1);
+ fsmenu_insert_entry(sfile->dir, 1, 0);
if(sfile->type==FILE_MAIN) { /* DATABROWSE */
if (sfile->menup) { /* with value pointing to ID block index */
@@ -2017,7 +1834,7 @@ void winqreadfilespace(ScrArea *sa, void *spacedata, BWinEvent *evt)
strcat(sfile->dir, sfile->filelist[act].relname);
strcat(sfile->dir,"/");
BLI_cleanup_dir(G.sce, sfile->dir);
- freefilelist(sfile);
+ freefilelist(sfile);
sfile->ofs= 0;
do_draw= 1;
}
diff --git a/source/blender/src/fsmenu.c b/source/blender/src/fsmenu.c
new file mode 100644
index 00000000000..1d03291b135
--- /dev/null
+++ b/source/blender/src/fsmenu.c
@@ -0,0 +1,260 @@
+/**
+ * $Id: fsmenu.c 11698 2007-08-19 12:22:51Z elubie $
+ *
+ * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
+ *
+ * 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. The Blender
+ * Foundation also sells licenses for use in proprietary software under
+ * the Blender License. See http://www.blender.org/BL/ for information
+ * about this.
+ *
+ * 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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
+ * All rights reserved.
+ *
+ * The Original Code is: all of this file.
+ *
+ * Contributor(s): none yet.
+ *
+ * ***** END GPL/BL DUAL LICENSE BLOCK *****
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include <math.h>
+
+#include "MEM_guardedalloc.h"
+
+#include "BMF_Api.h"
+
+#include "BLI_blenlib.h"
+#include "BLI_linklist.h"
+#include "BLI_dynstr.h"
+#include "BIF_usiblender.h"
+
+
+#include "BIF_fsmenu.h" /* include ourselves */
+
+
+/* FSMENU HANDLING */
+
+ /* FSMenuEntry's without paths indicate seperators */
+typedef struct _FSMenuEntry FSMenuEntry;
+struct _FSMenuEntry {
+ FSMenuEntry *next;
+
+ char *path;
+ short save;
+};
+
+static FSMenuEntry *fsmenu= 0;
+
+int fsmenu_get_nentries(void)
+{
+ FSMenuEntry *fsme;
+ int count= 0;
+
+ for (fsme= fsmenu; fsme; fsme= fsme->next)
+ count++;
+
+ return count;
+}
+int fsmenu_is_entry_a_seperator(int idx)
+{
+ FSMenuEntry *fsme;
+
+ for (fsme= fsmenu; fsme && idx; fsme= fsme->next)
+ idx--;
+
+ return (fsme && !fsme->path)?1:0;
+}
+char *fsmenu_get_entry(int idx)
+{
+ FSMenuEntry *fsme;
+
+ for (fsme= fsmenu; fsme && idx; fsme= fsme->next)
+ idx--;
+
+ return fsme?fsme->path:NULL;
+}
+char *fsmenu_build_menu(void)
+{
+ DynStr *ds= BLI_dynstr_new();
+ FSMenuEntry *fsme;
+ char *menustr;
+
+ for (fsme= fsmenu; fsme; fsme= fsme->next) {
+ if (!fsme->path) {
+ /* clean consecutive seperators and ignore trailing ones */
+ if (fsme->next) {
+ if (fsme->next->path) {
+ BLI_dynstr_append(ds, "%l|");
+ } else {
+ FSMenuEntry *next= fsme->next;
+ fsme->next= next->next;
+ MEM_freeN(next);
+ }
+ }
+ } else {
+ if (fsme->save) {
+ BLI_dynstr_append(ds, "o ");
+ } else {
+ BLI_dynstr_append(ds, " ");
+ }
+ BLI_dynstr_append(ds, fsme->path);
+ if (fsme->next) BLI_dynstr_append(ds, "|");
+ }
+ }
+
+ menustr= BLI_dynstr_get_cstring(ds);
+ BLI_dynstr_free(ds);
+ return menustr;
+}
+static FSMenuEntry *fsmenu_get_last_separator(void)
+{
+ FSMenuEntry *fsme, *lsep=NULL;
+
+ for (fsme= fsmenu; fsme; fsme= fsme->next)
+ if (!fsme->path)
+ lsep= fsme;
+
+ return lsep;
+}
+
+static FSMenuEntry *fsmenu_get_first_separator(void)
+{
+ FSMenuEntry *fsme, *lsep=NULL;
+
+ for (fsme= fsmenu; fsme; fsme= fsme->next)
+ if (!fsme->path) {
+ lsep= fsme;
+ break;
+ }
+
+ return lsep;
+}
+
+void fsmenu_insert_entry(char *path, int sorted, short save)
+{
+ FSMenuEntry *prev;
+ FSMenuEntry *fsme;
+
+ if (save) {
+ prev = fsmenu_get_first_separator();
+ } else {
+ prev = fsmenu_get_last_separator();
+ }
+ fsme= prev?prev->next:fsmenu;
+
+ for (; fsme; prev= fsme, fsme= fsme->next) {
+ if (fsme->path) {
+ if (BLI_streq(path, fsme->path)) {
+ return;
+ } else if (sorted && strcmp(path, fsme->path)<0) {
+ break;
+ }
+ } else {
+ // if we're bookmarking this, file should come
+ // before the last separator, only automatically added
+ // current dir go after the last sep.
+ if (save) {
+ break;
+ }
+ }
+ }
+
+ fsme= MEM_mallocN(sizeof(*fsme), "fsme");
+ fsme->path= BLI_strdup(path);
+ fsme->save = save;
+
+ if (prev) {
+ fsme->next= prev->next;
+ prev->next= fsme;
+ } else {
+ fsme->next= fsmenu;
+ fsmenu= fsme;
+ }
+}
+void fsmenu_append_separator(void)
+{
+ if (fsmenu) {
+ FSMenuEntry *fsme= fsmenu;
+
+ while (fsme->next) fsme= fsme->next;
+
+ fsme->next= MEM_mallocN(sizeof(*fsme), "fsme");
+ fsme->next->next= NULL;
+ fsme->next->path= NULL;
+ }
+}
+void fsmenu_remove_entry(int idx)
+{
+ FSMenuEntry *prev= NULL, *fsme= fsmenu;
+
+ for (fsme= fsmenu; fsme && idx; prev= fsme, fsme= fsme->next)
+ idx--;
+
+ if (fsme) {
+ if (prev) {
+ prev->next= fsme->next;
+ } else {
+ fsmenu= fsme->next;
+ if (fsme->save) {
+ if (prev) {
+ prev->next= fsme->next;
+ } else {
+ fsmenu= fsme->next;
+ }
+ // you should only be able to remove entries that were
+ // not added by default
+ if (fsme->path) {
+ MEM_freeN(fsme->path);
+ }
+ MEM_freeN(fsme);
+ }
+ }
+ }
+}
+
+void fsmenu_write_file(const char *filename)
+{
+ FSMenuEntry *fsme= fsmenu;
+
+ FILE *fp = fopen(filename, "w");
+ if (!fp) return;
+
+ for (fsme= fsmenu; fsme; fsme= fsme->next) {
+ if (fsme->path && fsme->save) {
+ fprintf(fp, "%s\n", fsme->path);
+ }
+ }
+ fclose(fp);
+}
+
+void fsmenu_free(void)
+{
+ FSMenuEntry *fsme= fsmenu;
+
+ while (fsme) {
+ FSMenuEntry *n= fsme->next;
+
+ if (fsme->path) MEM_freeN(fsme->path);
+ MEM_freeN(fsme);
+
+ fsme= n;
+ }
+}
+
+
+
diff --git a/source/blender/src/glutil.c b/source/blender/src/glutil.c
index 248d36dcb1e..13922bb7eef 100644
--- a/source/blender/src/glutil.c
+++ b/source/blender/src/glutil.c
@@ -50,6 +50,11 @@
#include "BIF_glutil.h"
#include "BIF_mywindow.h"
+#ifndef GL_CLAMP_TO_EDGE
+#define GL_CLAMP_TO_EDGE 0x812F
+#endif
+
+
/* Invert line handling */
#define glToggle(mode, onoff) (((onoff)?glEnable:glDisable)(mode))
@@ -263,10 +268,17 @@ void glaDrawPixelsTex(float x, float y, int img_w, int img_h, int format, void *
int nsubparts_x= (img_w+(tex_w-1))/tex_w;
int nsubparts_y= (img_h+(tex_h-1))/tex_h;
- glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
+ /* Specify the color outside this function, and tex will modulate it.
+ * This is useful for changing alpha without using glPixelTransferf()
+ */
+ glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
glPixelStorei(GL_UNPACK_ROW_LENGTH, img_w);
glBindTexture(GL_TEXTURE_2D, texid);
+ /* don't want nasty border artifacts */
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+
for (subpart_y=0; subpart_y<nsubparts_y; subpart_y++) {
for (subpart_x=0; subpart_x<nsubparts_x; subpart_x++) {
int subpart_w= (subpart_x==nsubparts_x-1)?(img_w-subpart_x*tex_w):tex_w;
@@ -278,17 +290,16 @@ void glaDrawPixelsTex(float x, float y, int img_w, int img_h, int format, void *
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, subpart_w, subpart_h, GL_RGBA, GL_FLOAT, &f_rect[(subpart_y*tex_w)*img_w*4 + (subpart_x*tex_w)*4]);
else
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, subpart_w, subpart_h, GL_RGBA, GL_UNSIGNED_BYTE, &uc_rect[(subpart_y*tex_w)*img_w*4 + (subpart_x*tex_w)*4]);
-
- glColor3ub(255, 255, 255);
+
glEnable(GL_TEXTURE_2D);
glBegin(GL_QUADS);
glTexCoord2f(0, 0);
glVertex2f(rast_x, rast_y);
- glTexCoord2f((float) subpart_w/tex_w, 0);
+ glTexCoord2f((float) (subpart_w-1)/tex_w, 0);
glVertex2f(rast_x+subpart_w*xzoom, rast_y);
- glTexCoord2f((float) subpart_w/tex_w, (float) subpart_h/tex_h);
+ glTexCoord2f((float) (subpart_w-1)/tex_w, (float) subpart_h/tex_h);
glVertex2f(rast_x+subpart_w*xzoom, rast_y+subpart_h*yzoom);
glTexCoord2f(0, (float) subpart_h/tex_h);
diff --git a/source/blender/src/header_imasel.c b/source/blender/src/header_imasel.c
index c99112248b7..2172651d2ff 100644
--- a/source/blender/src/header_imasel.c
+++ b/source/blender/src/header_imasel.c
@@ -49,7 +49,9 @@
#include "DNA_ID.h"
#include "DNA_screen_types.h"
#include "DNA_space_types.h"
+#include "DNA_userdef_types.h"
+#include "BIF_filelist.h"
#include "BIF_gl.h"
#include "BIF_imasel.h"
#include "BIF_interface.h"
@@ -65,26 +67,30 @@
void do_imasel_buttons(short event)
{
SpaceImaSel *simasel;
- char name[256];
-
+
simasel= curarea->spacedata.first;
if(curarea->win==0) return;
switch(event) {
- case B_IMASELHOME:
+ case B_SORTIMASELLIST:
+ BIF_filelist_sort(simasel->files, simasel->sort);
+ scrarea_queue_winredraw(curarea);
break;
- case B_IMASELREMOVEBIP:
-
- if(bitset(simasel->fase, IMS_FOUND_BIP)){
-
- strcpy(name, simasel->dir);
- strcat(name, ".Bpib");
-
- remove(name);
-
- simasel->fase &= ~ IMS_FOUND_BIP;
+ case B_RELOADIMASELDIR:
+ BIF_filelist_free(simasel->files);
+ scrarea_queue_winredraw(curarea);
+ break;
+ case B_FILTERIMASELDIR:
+ if (simasel->flag & FILE_FILTER) {
+ BIF_filelist_setfilter(simasel->files,simasel->filter);
+ BIF_filelist_filter(simasel->files);
+ scrarea_queue_winredraw(curarea);
+ } else {
+ BIF_filelist_setfilter(simasel->files,0);
+ BIF_filelist_filter(simasel->files);
+ scrarea_queue_winredraw(curarea);
}
break;
}
@@ -94,9 +100,9 @@ void imasel_buttons(void)
{
SpaceImaSel *simasel;
uiBlock *block;
- short xco;
+ short xco, xcotitle;
char naam[256];
-
+
simasel= curarea->spacedata.first;
sprintf(naam, "header %d", curarea->headwin);
@@ -117,26 +123,76 @@ void imasel_buttons(void)
if(curarea->full) uiDefIconBut(block, BUT,B_FULL, ICON_SPLITSCREEN, xco,0,XIC,YIC, 0, 0, 0, 0, 0, "");
else uiDefIconBut(block, BUT,B_FULL, ICON_FULLSCREEN, xco,0,XIC,YIC, 0, 0, 0, 0, 0, "");
+ /* SORT TYPE */
xco+=XIC;
- if (simasel->title){
- xco+=25;
- glRasterPos2i(xco, 4);
- BMF_DrawString(G.font, simasel->title);
- xco+=BMF_GetStringWidth(G.fonts, simasel->title);
- xco+=25;
- }
-
uiBlockBeginAlign(block);
- uiDefIconBut(block, BUT, B_IMASELREMOVEBIP, ICON_BPIBFOLDER_X, xco+=XIC,0,XIC,YIC, 0, 0, 0, 0, 0, "");/* remove */
+ uiDefIconButS(block, ROW, B_SORTIMASELLIST, ICON_SORTALPHA, xco+=XIC,0,XIC,YIC, &simasel->sort, 1.0, 0.0, 0, 0, "Sorts files alphabetically");
+ uiDefIconButS(block, ROW, B_SORTIMASELLIST, ICON_SORTBYEXT, xco+=XIC,0,XIC,YIC, &simasel->sort, 1.0, 3.0, 0, 0, "Sorts files by extension");
+ uiDefIconButS(block, ROW, B_SORTIMASELLIST, ICON_SORTTIME, xco+=XIC,0,XIC,YIC, &simasel->sort, 1.0, 1.0, 0, 0, "Sorts files by time");
+ uiDefIconButS(block, ROW, B_SORTIMASELLIST, ICON_SORTSIZE, xco+=XIC,0,XIC,YIC, &simasel->sort, 1.0, 2.0, 0, 0, "Sorts files by size");
+ uiBlockEndAlign(block);
+
+ cpack(0x0);
+ xco+=XIC+10;
+ uiDefIconButBitS(block, TOG, FILE_BOOKMARKS, B_RELOADIMASELDIR, ICON_BOOKMARKS,xco+=XIC,0,XIC,YIC, &simasel->flag, 0, 0, 0, 0, "Toggles Bookmarks on/off");
+ xco+=XIC+10;
+
+ xcotitle= xco;
+ xco+= BIF_GetStringWidth(G.font, simasel->title, (U.transopts & USER_TR_BUTTONS));
- uiDefIconButS(block, TOG|BIT|0, B_REDR, ICON_BPIBFOLDERGREY, xco+=XIC,0,XIC,YIC, &simasel->mode, 0, 0, 0, 0, "Toggles display of directory information");/* dir */
- uiDefIconButS(block, TOG|BIT|1, B_REDR, ICON_INFO, xco+=XIC,0,XIC,YIC, &simasel->mode, 0, 0, 0, 0, "Toggles display of selected image information");/* info */
- uiDefIconButS(block, TOG|BIT|2, B_REDR, ICON_IMAGE_COL, xco+=XIC,0,XIC,YIC, &simasel->mode, 0, 0, 0, 0, "");/* image */
- uiDefIconButS(block, TOG|BIT|3, B_REDR, ICON_MAGNIFY, xco+=XIC,0,XIC,YIC, &simasel->mode, 0, 0, 0, 0, "Toggles magnified view of thumbnail of images under mouse pointer");/* magnify */
+ if(simasel->pupmenu && simasel->menup) {
+ uiDefButS(block, MENU, B_NOP, simasel->pupmenu, xco+10,0,90,20, simasel->menup, 0, 0, 0, 0, "");
+ xco+= 100;
+ }
+ uiBlockBeginAlign(block);
+ uiDefIconButBitS(block, TOG, FILE_HIDE_DOT, B_RELOADIMASELDIR, ICON_GHOST,xco+=XIC,0,XIC,YIC, &simasel->flag, 0, 0, 0, 0, "Hides dot files");
uiBlockEndAlign(block);
+ xco+=20;
+
+ uiDefIconButBitS(block, TOG, FILE_FILTER, B_FILTERIMASELDIR, ICON_SORTBYEXT,xco+=XIC,0,XIC,YIC, &simasel->flag, 0, 0, 0, 0, "Filter files");
+ if (simasel->flag & FILE_FILTER) {
+ xco+=4;
+ uiBlockBeginAlign(block);
+ uiDefIconButBitS(block, TOG, IMAGEFILE, B_FILTERIMASELDIR, ICON_IMAGE_COL,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show images");
+ uiDefIconButBitS(block, TOG, BLENDERFILE, B_FILTERIMASELDIR, ICON_BLENDER,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show .blend files");
+ uiDefIconButBitS(block, TOG, MOVIEFILE, B_FILTERIMASELDIR, ICON_SEQUENCE,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show movies");
+ uiDefIconButBitS(block, TOG, PYSCRIPTFILE, B_FILTERIMASELDIR, ICON_PYTHON,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show python scripts");
+ uiDefIconButBitS(block, TOG, FTFONTFILE, B_FILTERIMASELDIR, ICON_SYNTAX,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show fonts");
+ uiDefIconButBitS(block, TOG, SOUNDFILE, B_FILTERIMASELDIR, ICON_SOUND,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show sound files");
+ uiDefIconButBitS(block, TOG, TEXTFILE, B_FILTERIMASELDIR, ICON_TEXT,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show text files");
+ uiDefIconButBitS(block, TOG, FOLDERFILE, B_FILTERIMASELDIR, ICON_FILESEL,xco+=XIC,0,XIC,YIC, &simasel->filter, 0, 0, 0, 0, "Show folders");
+ uiBlockEndAlign(block);
+ }
+
+ uiDefButBitS(block, TOG, FILE_STRINGCODE, 0, "Relative Paths", xco+=XIC+20,0,100,YIC, &simasel->flag, 0, 0, 0, 0, "Makes sure returned paths are relative to the current .blend file");
+ xco+=90;
+
+ if(simasel->type==FILE_LOADLIB) {
+ uiBlockBeginAlign(block);
+ uiDefButBitS(block, TOGN, FILE_LINK, B_REDR, "Append", xco+=XIC,0,100,YIC, &simasel->flag, 0, 0, 0, 0, "Copies selected data into current project");
+ uiDefButBitS(block, TOG, FILE_LINK, B_REDR, "Link", xco+=100,0,100,YIC, &simasel->flag, 0, 0, 0, 0, "Creates a link to selected data from current project");
+ uiBlockEndAlign(block);
+ uiBlockBeginAlign(block);
+ uiDefButBitS(block, TOG, FILE_AUTOSELECT, B_REDR, "Autosel", xco+=125,0,65,YIC, &simasel->flag, 0, 0, 0, 0, "Autoselect imported objects");
+ uiDefButBitS(block, TOG, FILE_ACTIVELAY, B_REDR, "Active Layer", xco+=65,0,80,YIC, &simasel->flag, 0, 0, 0, 0, "Append object(s) in active layer");
+ uiDefButBitS(block, TOG, FILE_ATCURSOR, B_REDR, "At Cursor", xco+=80,0,65,YIC, &simasel->flag, 0, 0, 0, 0, "Append object(s) at cursor, use centroid if more than one object is selected");
+ uiBlockEndAlign(block);
+
+ xco+= 100; // scroll
+
+ } else if(simasel->type==FILE_BLENDER) {
+ uiDefButBitI(block, TOGN, G_FILE_NO_UI, B_REDR, "Load UI", xco+=XIC,0,80,YIC, &G.fileflags, 0, 0, 0, 0, "Load the UI setup as well as the scene data");
+ xco+= 100; // scroll
+ }
+
+ glRasterPos2f((float)xcotitle, 5.0);
+ BIF_RasterPos((float)xcotitle, 5.0); // stupid texture fonts
+ BIF_ThemeColor(TH_TEXT);
+ BIF_DrawString(uiBlockGetCurFont(block), simasel->title, (U.transopts & USER_TR_BUTTONS));
+
/* always do as last */
curarea->headbutlen= xco+2*XIC;
uiDrawBlock(block);
-}
+} \ No newline at end of file
diff --git a/source/blender/src/header_info.c b/source/blender/src/header_info.c
index aee2e2c620f..685da07f88f 100644
--- a/source/blender/src/header_info.c
+++ b/source/blender/src/header_info.c
@@ -105,6 +105,7 @@
#include "BSE_editipo.h"
#include "BSE_filesel.h"
+#include "BIF_imasel.h"
#include "BSE_headerbuttons.h"
#include "BSE_node.h"
#include "BSE_sequence.h"
@@ -839,6 +840,9 @@ static void do_info_filemenu(void *arg, int event)
case 6: /* save image */
BIF_save_rendered_image_fs();
break;
+ case 7:
+ activate_imageselect(FILE_LOADLIB, "Load Library", G.lib, 0);
+ break;
case 22: /* save runtime */
activate_fileselect(FILE_SPECIAL, "Save Runtime", "", write_runtime_check);
break;
@@ -991,6 +995,7 @@ static uiBlock *info_filemenu(void *arg_unused)
uiDefBut(block, SEPR, 0, "", 0, yco-=6, menuwidth, 6, NULL, 0.0, 0.0, 0, 0, "");
uiDefIconTextBut(block, BUTM, 1, ICON_BLANK1, "Append or Link|Shift F1", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 3, "");
+ uiDefIconTextBut(block, BUTM, 1, ICON_BLANK1, "Append or Link (Image Browser)|Ctrl F1", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 7, "");
uiDefIconTextBlockBut(block, info_file_importmenu, NULL, ICON_RIGHTARROW_THIN, "Import", 0, yco-=20, menuwidth, 19, "");
uiDefIconTextBlockBut(block, info_file_exportmenu, NULL, ICON_RIGHTARROW_THIN, "Export", 0, yco-=20, menuwidth, 19, "");
diff --git a/source/blender/src/headerbuttons.c b/source/blender/src/headerbuttons.c
index 3d03adbc4bb..adc40683bc0 100644
--- a/source/blender/src/headerbuttons.c
+++ b/source/blender/src/headerbuttons.c
@@ -709,7 +709,12 @@ void do_global_buttons(unsigned short event)
else return;
if(*menunr== -2) {
- activate_databrowse((ID *)lockpoin, ID_MA, 0, B_MATBROWSE, menunr, do_global_buttons);
+ if(G.qual & LR_CTRLKEY) {
+ activate_databrowse_imasel((ID *)lockpoin, ID_MA, 0, B_MATBROWSE, menunr, do_global_buttons);
+ }
+ else {
+ activate_databrowse((ID *)lockpoin, ID_MA, 0, B_MATBROWSE, menunr, do_global_buttons);
+ }
return;
}
diff --git a/source/blender/src/imasel.c b/source/blender/src/imasel.c
index 6c232ea6464..78fc3f1be2a 100644
--- a/source/blender/src/imasel.c
+++ b/source/blender/src/imasel.c
@@ -57,864 +57,29 @@
#include "BKE_global.h"
#include "BIF_imasel.h"
+#include "BIF_filelist.h"
#include "BIF_space.h"
#include "BIF_screen.h"
#include "blendef.h"
#include "mydevice.h"
-#ifndef WIN32
-#include <dirent.h>
-#endif
-
-#include <sys/stat.h>
-#include "datatoc.h"
-
-/* locals */
-void longtochar(char *des, unsigned int *src, int size);
-void chartolong(unsigned int *des, char *src, int size);
-int dir_compare(const void *a1, const void *a2);
-void issort( int te, ImaDir **firstentry);
-int ima_compare(const void *a1, const void *a2);
-void imsort(OneSelectableIma **firstentry);
-void append_pib(SpaceImaSel *simasel, OneSelectableIma *ima);
-void add_ima(int who, SpaceImaSel *simasel, ImaDir *direntry);
-
-/* implementation */
-int bitset(int l, int bit)
-{ return (( l & bit) == bit); }
-
-void longtochar(char *des, unsigned int *src, int size)
-{ int i;for (i = 0; i<size; i++){ des[i] = src[i] & 0xFF; }}
-
-void chartolong(unsigned int *des, char *src, int size)
-{ int i;for (i = 0; i<size; i++){ des[i] = src[i]; }}
-
-int dir_compare(const void *a1, const void *a2)
-{
- ImaDir **in1, **in2;
- ImaDir *use1, *use2;
-
- in1= (ImaDir **)a1;
- in2= (ImaDir **)a2;
-
- use1 = *in1;
- use2 = *in2;
-
- return BLI_strcasecmp(use1->name, use2->name);
-}
-
-void issort( int te, ImaDir **firstentry)
-{
- ImaDir **sort;
- ImaDir *use;
- int i = 0;
-
- sort = MEM_mallocN(te * sizeof(void *), "dir Sorteer temp");
- use = *firstentry;
-
- while (use){
- sort[i++] = use;
- use = use->next;
- }
-
- qsort (sort, te, sizeof(void *), dir_compare);
-
- *firstentry = sort[0];
- use = *firstentry;
-
-
- for (i=0; i<te; i++){
- if (i != 0) use->prev = sort[i-1]; else use->prev = 0;
- if (i != te-1) use->next = sort[i+1]; else use->next = 0;
-
- use = use->next;
- }
-
- MEM_freeN(sort);
-}
-
-
-int ima_compare(const void *a1, const void *a2)
-{
- OneSelectableIma **in1, **in2;
- OneSelectableIma *use1, *use2;
-
- in1= (OneSelectableIma **)a1;
- in2= (OneSelectableIma **)a2;
-
- use1 = *in1; use2 = *in2;
- return BLI_strcasecmp(use1->file_name, use2->file_name);
-}
-
-void imsort(OneSelectableIma **firstentry)
-{
- OneSelectableIma **sort;
- OneSelectableIma *use;
- int tot = 0, i = 0;
-
- use = *firstentry;
- while (use){
- tot++;
- use = use->next;
- }
-
- if (tot){
- sort = MEM_mallocN(tot * sizeof(void *), "Sorteer imsort temp");
- use = *firstentry;
- while (use){
- sort[i++] = use;
- use = use->next;
- }
-
- qsort (sort, tot, sizeof(void *), ima_compare);
-
- *firstentry = sort[0];
- use = *firstentry;
- for (i=0; i<tot; i++){
- if (i != 0) use->prev = sort[i-1]; else use->prev = 0;
- if (i != tot-1) use->next = sort[i+1]; else use->next = 0;
-
- use = use->next;
- }
- MEM_freeN(sort);
- }
-}
-
-static int write_msb_int(int fd, int i) {
- unsigned int ui= (unsigned int) i;
- unsigned char buf[4];
- buf[0]= (ui>>24)&0xFF;
- buf[1]= (ui>>16)&0xFF;
- buf[2]= (ui>>8)&0xFF;
- buf[3]= (ui>>0)&0xFF;
- return write(fd, buf, 4);
-}
-static int write_msb_short(int fd, short s) {
- unsigned short us= (unsigned short) s;
- unsigned char buf[2];
- buf[0]= (us>>8)&0xFF;
- buf[1]= (us>>0)&0xFF;
- return write(fd, buf, 2);
-}
-
-static int read_msb_int(int fd, int *i_r) {
- unsigned char buf[4];
- int rcount= read(fd, buf, 4);
-
- if (i_r)
- *i_r= (buf[0]<<24)|(buf[1]<<16)|(buf[2]<<8)|(buf[3]<<0);
-
- return rcount;
-}
-static int read_msb_short(int fd, short *s_r) {
- unsigned char buf[2];
- int rcount= read(fd, buf, 2);
-
- if (s_r)
- *s_r= (buf[0]<<8)|(buf[1]<<0);
-
- return rcount;
-}
-
-void append_pib(SpaceImaSel *simasel, OneSelectableIma *ima)
-{
- int file;
- char name[FILE_MAXDIR+FILE_MAXFILE];
-
- if ( bitset (simasel->fase, IMS_WRITE_NO_BIP)) return;
-
- strcpy(name, simasel->dir);
- strcat(name, ".Bpib");
-
- file = open(name, O_BINARY|O_APPEND | O_RDWR | O_CREAT, 0666);
- if (file == -1) {
- /* printf("Could not write .Bpib file in dir %s\n", simasel->dir); */
- simasel->fase |= IMS_WRITE_NO_BIP;
- return;
- }
-
- lseek(file, 0, SEEK_END);
-
- write(file, "BIP2", 4);
- write_msb_int(file, ima->ibuf_type);
- write_msb_int(file, 0);
- write_msb_int(file, 0);
- write_msb_int(file, 0);
- write_msb_short(file, ima->cmap);
- write_msb_short(file, ima->image);
- write_msb_short(file, ima->draw_me);
- write_msb_short(file, ima->rt);
- write_msb_short(file, ima->sx);
- write_msb_short(file, ima->sy);
- write_msb_short(file, ima->ex);
- write_msb_short(file, ima->ey);
- write_msb_short(file, ima->dw);
- write_msb_short(file, ima->dh);
- write_msb_short(file, ima->selectable);
- write_msb_short(file, ima->selected);
- write_msb_int(file, ima->mtime);
- write_msb_int(file, ima->disksize);
- write(file, ima->file_name, 64);
- write_msb_short(file, ima->orgx);
- write_msb_short(file, ima->orgy);
- write_msb_short(file, ima->orgd);
- write_msb_short(file, ima->anim);
- write_msb_int(file, 0); /* pad to 128 boundary */
- write(file, ima->pict_rect, 3968);
-
- close(file);
-}
-
-void write_new_pib(SpaceImaSel *simasel)
-{
- OneSelectableIma *ima;
- char name[FILE_MAXDIR+FILE_MAXFILE];
-
- strcpy(name, simasel->dir);
- strcat(name, ".Bpib");
- remove(name);
-
- ima = simasel->first_sel_ima;
- while (ima) {
- append_pib(simasel, ima);
- ima = ima->next;
- }
-}
-
-void free_ima_dir(ImaDir *firstdir)
-{
- ImaDir *n;
-
- while(firstdir){
- n = firstdir->next;
- MEM_freeN(firstdir);
- firstdir = n;
- }
-}
-void free_sel_ima(OneSelectableIma *firstima)
-{
- OneSelectableIma *n;
-
- while(firstima){
-
- if (firstima->pict) {
- IMB_freeImBuf(firstima->pict);
- }
- n = firstima->next;
- MEM_freeN(firstima);
- firstima = n;
- }
-}
-
-void check_for_pib(SpaceImaSel *simasel)
-{
- ImaDir *direntry;
-
- direntry = simasel->firstfile;
- while(direntry){
- if ((strlen(direntry->name) > 4) && (0==strcmp(direntry->name, ".Bpib")) ){
- simasel->fase |= IMS_FOUND_BIP;
- direntry = 0;
- }else{
- direntry = direntry->next;
- }
- }
-}
-
-void clear_ima_dir(SpaceImaSel *simasel)
-{
- if(simasel->first_sel_ima) free_sel_ima(simasel->first_sel_ima);
- if(simasel->firstdir) free_ima_dir(simasel->firstdir);
- if(simasel->firstfile) free_ima_dir(simasel->firstfile);
-
- simasel->first_sel_ima = 0;
- simasel->firstdir = 0;
- simasel->firstfile = 0;
-
- simasel->totaldirs = 0;
- simasel->totalfiles = 0;
- simasel->totalima = 0;
- simasel->topdir = -1;
- simasel->topfile = -1;
- simasel->topima = 0;
- simasel->image_slider = 0.0;
- simasel->slider_height = 0.0;
- simasel->slider_space = 0.0;
- simasel->hilite = -1;
- simasel->curimax = 0;
- simasel->curimay = 0;
-
- simasel->total_selected = 0;
- simasel->fase = 0;
- simasel->subfase = 0;
- simasel->imafase = 0;
- simasel->ima_redraw = 0;
-}
-
-int get_ima_dir(char *dirname, int dtype, int *td, ImaDir **first)
-{
- DIR *dirp;
- struct dirent *dep;
- struct ImaDir *temp;
- struct ImaDir *dnext = NULL, *fnext;
- struct stat status;
- char olddir[FILE_MAXDIR+FILE_MAXFILE];
- char getdirname[FILE_MAXDIR+FILE_MAXFILE];
- int /* i=0, */ tot=0;
- int isdir;
-
- if(!BLI_getwdN(olddir)) return -1;
-
- if (chdir(dirname) == -1) return(-1);
-
- strcpy(getdirname, ".");
-
- dirp = (DIR *) opendir(getdirname);
- if (dirp == NULL) return (-1);
-
- waitcursor(1);
-
- while((dep = (struct dirent*) readdir(dirp)) != NULL){
-
- strcpy(getdirname, dirname);
- strcat(getdirname,dep->d_name);
-
- stat(getdirname, &status);
- isdir = S_ISDIR(status.st_mode);
-
- if ( ((dtype == IMS_DIR) && isdir) || ((dtype == IMS_FILE) && !isdir)){
- /* yes, searching for this type */
- tot++;
- if (tot == 1){
- dnext = MEM_callocN(sizeof(struct ImaDir), "get first");
- *first = dnext;
-
- dnext->prev = 0;
- dnext->next = 0;
- }else{
- fnext = MEM_callocN(sizeof(struct ImaDir), "get nextdir");
- dnext->next = fnext;
-
- temp = dnext;
- dnext = fnext;
-
- dnext ->prev = temp;
- dnext ->next = 0;
- }
-
- dnext->type = dtype;
- dnext->selected = 0;
- dnext->hilite = 0;
-
- dnext->mtime = status.st_ctime;
- dnext->size = (int)status.st_size;
- strcpy(dnext->name, dep->d_name);
- }
- }
- closedir(dirp);
-
- if (tot) issort(tot, first);
-
- waitcursor(0);
-
- *td = tot;
-
- chdir (olddir);
-
- return (tot);
-}
-
-void imadir_parent(SpaceImaSel *simasel)
-{
-
-#ifdef WIN32
- if (strlen(simasel->dir) > 1){
- simasel->dir[strlen(simasel->dir)-1] = 0;
- while(simasel->dir[strlen(simasel->dir)-1] != '\\'){
- if(strlen(simasel->dir)==0) break;
- simasel->dir[strlen(simasel->dir)-1] = 0;
- }
- }
-#else
- if (strlen(simasel->dir) > 1){
- simasel->dir[strlen(simasel->dir)-1] = 0;
- while(simasel->dir[strlen(simasel->dir)-1] != '/') {
- if(strlen(simasel->dir)==0) break;
- simasel->dir[strlen(simasel->dir)-1] = 0;
- }
- }
-#endif
-}
-
-
-void get_next_image(SpaceImaSel *simasel)
-{
- OneSelectableIma * ima;
- ImBuf * ibuf;
- struct anim * anim;
- int i = 0, size;
- char name[FILE_MAXDIR+FILE_MAXFILE];
-
- ima = simasel->first_sel_ima;
- if (ima == 0){
- simasel->imafase = 0;
- simasel->fase |= IMS_KNOW_IMA;
- simasel->fase &= ~IMS_DOTHE_IMA;
- return;
- }
- if (simasel->imafase > simasel->totalima){
- simasel->imafase = 0;
- simasel->fase &= ~IMS_DOTHE_IMA;
- simasel->fase |= IMS_KNOW_IMA;
- }
-
- ima = simasel->first_sel_ima;
- i = 0;
- while(i < simasel->imafase){
- if ((ima) && (ima->next)) ima = ima->next;
- i++;
- }
-
- if (ima->image == 0) {
- if (ima->anim == 1) {
- /* open movie, get len, get middle picture */
-
- strcpy(name, simasel->dir);
- strcat(name, ima->file_name);
-
- anim = IMB_open_anim(name, IB_rect);
-
- if (anim == 0) {
- // ibuf= IMB_loadiffmem((int*)datatoc_cmovie_tga, IB_rect);
- ibuf= IMB_ibImageFromMemory((int *)datatoc_cmovie_tga, datatoc_cmovie_tga_size, IB_rect);
- }
- else{
- int animlen;
-
- ibuf = IMB_anim_nextpic(anim);
- IMB_freeImBuf(ibuf);
-
- animlen= IMB_anim_get_duration(anim);
- ibuf = IMB_anim_absolute(anim, animlen / 2);
-
- if(ibuf) {
- //get icon dimensions for movie
- ima->orgx = ibuf->x;
- ima->orgy = ibuf->y;
-// ima->orgd = ibuf->depth;
-
- if (ima->orgx > ima->orgy){
- ima->dw = 64;
- ima->dh = (short)(62 * ((float)ima->orgy / (float)ima->orgx));
- }else{
- ima->dw = (short)(64 * ((float)ima->orgx / (float)ima->orgy));
- ima->dh = 62;
- }
- }
-
- IMB_free_anim(anim);
- }
- }
- else {
-
- strcpy(name, simasel->dir);
- strcat(name, ima->file_name);
-
- ibuf = IMB_loadiffname(name, IB_rect);
- if(ibuf && ibuf->zbuf) IMB_freezbufImBuf(ibuf);
- }
-
- if (ibuf){
- if (ima->dw < 4) ima->dw = 4;
- if (ima->dh < 4) ima->dh = 4;
-
- IMB_scaleImBuf(ibuf, ima->dw, ima->dh);
- /* the whole cmap system is wacko */
-
- if (G.order==B_ENDIAN)
- IMB_convert_rgba_to_abgr(ibuf);
-
- ibuf->mincol = 0;
- ibuf->maxcol = 256;
- ibuf->cbits = 5;
- ibuf->depth = 8;
-
- IMB_freecmapImBuf(ibuf);
- ibuf->cmap = simasel->cmap->cmap;
-
- IMB_converttocmap(ibuf);
-
- /* copy ibuf->rect to ima->pict_rect */
- size = ima->dw * ima->dh; if (size > 3968) size = 3968;
- longtochar(ima->pict_rect, ibuf->rect, size);
-
- IMB_applycmap(ibuf);
- IMB_convert_rgba_to_abgr(ibuf);
-
- if (ima->pict) IMB_freeImBuf(ima->pict);
- ima->pict = ibuf;
- ibuf = 0;
- ima->cmap = 1;
- ima->image = 1;
-
- append_pib(simasel, ima);
- }
- }
- simasel->ima_redraw++;
- simasel->imafase ++;
- if (simasel->imafase == simasel->totalima){
- simasel->imafase = 0;
- simasel->fase &= ~IMS_DOTHE_IMA;
- simasel->fase |= IMS_KNOW_IMA;
- }
-}
-
-void add_ima(int who, SpaceImaSel *simasel, ImaDir *direntry)
-{
- OneSelectableIma *ima, *prev_ima;
- ImBuf *ibuf;
- char name[FILE_MAXDIR+FILE_MAXFILE];
-
- strcpy(name , simasel->dir);
- strcat(name , direntry->name);
-
- prev_ima = simasel->first_sel_ima;
- while((prev_ima)&&(prev_ima->next)){
- prev_ima = prev_ima->next;
- }
-
- ima = MEM_callocN(sizeof(OneSelectableIma), "OSIbip");
- if (direntry->type == IMS_IMA){
- /* Picture is an Image */
- ibuf = IMB_loadiffname(name, IB_test);
- if (ibuf){
- ima->anim = 0;
- ima->pict = ibuf;
- ima->ibuf_type= ibuf->ftype;
- ima->orgx = ibuf->x;
- ima->orgy = ibuf->y;
- ima->orgd = ibuf->depth;
-
- ima->dw = 64;
- ima->dh = 51;
- ima->cmap = 0;
- ima->image = 0;
- if (ima->orgx > ima->orgy){
- ima->dw = 64;
- ima->dh = (short)(62 * ((float)ima->orgy / (float)ima->orgx));
- }else{
- ima->dw = (short)(64 * ((float)ima->orgx / (float)ima->orgy));
- ima->dh = 62;
- }
- }else{
- printf("%s image with no imbuf ???\n", name);
- }
- ibuf = 0;
- }else{
- /* Picture is an Animation */
-
- ima->pict = 0;
- ima->anim = 1;
- ima->ibuf_type= 0;
- ima->orgx = 64;
- ima->orgy = 51;
- ima->orgd = 24;
-
- ima->dw = 64;
- ima->dh = 51;
- ima->cmap = 0;
- ima->image = 0;
- }
-
- strcpy(name, direntry->name); name[63] = 0;
- strcpy(ima->file_name, name);
- ima->disksize = (int)direntry->size;
- ima->mtime = (int)direntry->mtime;
-
- ima->next = 0;
- ima->prev = prev_ima;
-
- if (prev_ima) {
- prev_ima->next = ima;
- }else{
- simasel->first_sel_ima = ima;
- }
-
- simasel->ima_redraw++;
- simasel->totalima++;
-}
-
-
-void get_file_info(SpaceImaSel *simasel)
-{
- OneSelectableIma *prev_ima;
- ImaDir *direntry;
- char name[FILE_MAXDIR+FILE_MAXFILE];
- int i = 0;
-
- if (!simasel->firstfile){
- simasel->subfase = 0;
- simasel->fase |= IMS_KNOW_INF;
- simasel->fase &= ~IMS_DOTHE_INF;
- return;
- }
- if (simasel->subfase > simasel->totalfiles){
- simasel->subfase = 0;
- simasel->fase |= IMS_KNOW_INF;
- simasel->fase &= ~IMS_DOTHE_INF;
- }
-
- direntry = simasel->firstfile;
- while(i < simasel->subfase){
- direntry = direntry->next;
- i++;
- }
-
- prev_ima = simasel->first_sel_ima;
- while((prev_ima)&&(prev_ima->next)){
- prev_ima = prev_ima->next;
- }
-
- strcpy(name , simasel->dir);
- strcat(name , direntry->name);
-
- if(direntry->name[0] == '.') {
- direntry->type = IMS_NOIMA;
- } else {
- if (IMB_ispic(name)) {
- direntry->type = IMS_IMA;
- }else{
- if (IMB_isanim(name)) {
- direntry->type = IMS_ANIM;
- }else{
- direntry->type = IMS_NOIMA;
- }
- }
- }
-
- if (direntry->type != IMS_NOIMA){
- add_ima(1, simasel, direntry);
- }
-
- simasel->subfase++;
-
- if (simasel->subfase == simasel->totalfiles){
- simasel->subfase = 0;
- simasel->fase |= IMS_KNOW_INF;
- simasel->fase &= ~IMS_DOTHE_INF;
- }
-}
-
-/* Note: the thumbnails are saved in ABGR format in the .Bpib
-cache file */
-
-void get_pib_file(SpaceImaSel *simasel)
-{
- ImaDir *direntry, *prev_dir, *next_dir;
- OneSelectableIma *ima, *prev_ima;
- int flen;
- int dl, file, first, trd=0, rd, size, found, ima_added = 0;
- char name[FILE_MAXDIR+FILE_MAXFILE];
-
- if (bitset(simasel->fase , IMS_KNOW_BIP)) return;
-
- waitcursor(1);
-
- strcpy(name, simasel->dir);
- strcat(name, ".Bpib");
-
- file = open(name, O_BINARY|O_RDONLY);
-
- flen = BLI_filesize(file);
-
- simasel->totalima = 0;
- prev_ima = 0;
- first = 1;
- trd = 0;
-
- while(trd < flen){
- char header[5];
-
- ima = MEM_callocN(sizeof(OneSelectableIma), "Ima");
-
- rd= 0;
- rd+= read(file, header, 4);
- rd+= read_msb_int(file, &ima->ibuf_type);
- rd+= read_msb_int(file, NULL);
- rd+= read_msb_int(file, NULL);
- rd+= read_msb_int(file, NULL);
- rd+= read_msb_short(file, &ima->cmap);
- rd+= read_msb_short(file, &ima->image);
- rd+= read_msb_short(file, &ima->draw_me);
- rd+= read_msb_short(file, &ima->rt);
- rd+= read_msb_short(file, &ima->sx);
- rd+= read_msb_short(file, &ima->sy);
- rd+= read_msb_short(file, &ima->ex);
- rd+= read_msb_short(file, &ima->ey);
- rd+= read_msb_short(file, &ima->dw);
- rd+= read_msb_short(file, &ima->dh);
- rd+= read_msb_short(file, &ima->selectable);
- rd+= read_msb_short(file, &ima->selected);
- rd+= read_msb_int(file, &ima->mtime);
- rd+= read_msb_int(file, &ima->disksize);
- rd+= read(file, ima->file_name, 64);
- rd+= read_msb_short(file, &ima->orgx);
- rd+= read_msb_short(file, &ima->orgy);
- rd+= read_msb_short(file, &ima->orgd);
- rd+= read_msb_short(file, &ima->anim);
- rd+= read_msb_int(file, NULL);
- rd+= read(file, ima->pict_rect, 3968);
-
- found = 0;
-
- if (rd != sizeof(OneSelectableIma) || memcmp(header, "BIP2", 4)!=0) {
- printf("Error in Bpib file\n");
- strcpy(name, simasel->dir);
- strcat(name, ".Bpib");
- dl = remove(name);
- if (dl == 0) printf("corrupt Bpib file removed\n");
- trd = flen;
- } else {
- /* find matching direntry (if possible) */
- for (direntry= simasel->firstfile; direntry; direntry= direntry->next)
- if (BLI_streq(direntry->name, ima->file_name))
- break;
-
- if (direntry) {
- if (direntry->mtime == ima->mtime) {
- /* ima found and same, load pic */
- size = ima->dw * ima->dh;
- if (size > 3968) size = 3968;
- if (size) {
- ima->pict = IMB_allocImBuf(ima->dw, ima->dh, 24, IB_rect | IB_cmap, 0);
- chartolong(ima->pict->rect, ima->pict_rect, size);
- ima->pict->cmap = simasel->cmap->cmap;
- ima->pict->maxcol = 256;
- IMB_applycmap(ima->pict);
- IMB_convert_rgba_to_abgr(ima->pict);
- }
- ima->selected = 0;
- ima->selectable = 0;
-
- if(prev_ima) prev_ima->next = ima;
- ima->next = 0;
- ima->prev = prev_ima;
-
- prev_ima = ima;
-
- if (first){ first = 0;simasel->first_sel_ima = ima; }
- simasel->totalima++;
- found = 1;
- }
-
- /* remove direntry */
- prev_dir = direntry->prev;
- next_dir = direntry->next;
-
- if(prev_dir) prev_dir->next = next_dir;
- if(next_dir) next_dir->prev = prev_dir;
-
- MEM_freeN(direntry);
- }
- }
- if (!found) MEM_freeN(ima);
-
- trd+=rd;
- }
- close(file);
-
- direntry = simasel->firstfile;
-
- while(direntry){
-
- strcpy(name , simasel->dir);
- strcat(name , direntry->name);
-
- if (IMB_ispic(name)) {
- direntry->type = IMS_IMA;
- }else{
- if (IMB_isanim(name)) {
- direntry->type = IMS_ANIM;
- }else{
- direntry->type = IMS_NOIMA;
- }
- }
-
- if (direntry->type != IMS_NOIMA){
- prev_ima = simasel->first_sel_ima;
- while((prev_ima)&&(prev_ima->next)){
- prev_ima = prev_ima->next;
- }
- add_ima(2, simasel, direntry);
- ima_added = 1;
- }
- direntry = direntry->next;
- }
-
- imsort(&simasel->first_sel_ima);
-
- simasel->fase |= IMS_KNOW_BIP;
- simasel->fase |= IMS_KNOW_INF;
- simasel->fase |= IMS_KNOW_IMA;
-
- if (ima_added){
- simasel->fase |= IMS_DOTHE_IMA;
- simasel->fase &= ~IMS_KNOW_IMA;
- addafterqueue(curarea->win, AFTERIMASELGET, 1);
- }else{
- write_new_pib(simasel);
- }
-
- waitcursor(0);
-}
-
-void change_imadir(SpaceImaSel *simasel)
+void free_imasel(SpaceImaSel *simasel)
{
- ImaDir *direntry;
- int i;
-
- direntry = simasel->firstdir;
- for (i=0; i<simasel->hilite; i++){
- direntry = direntry->next;
+ /* do not free imasel itself */
+ if(simasel->files) {
+ BIF_filelist_freelib(simasel->files);
+ BIF_filelist_free(simasel->files);
+ MEM_freeN(simasel->files);
+ simasel->files = NULL;
}
-
- if(direntry==NULL);
- else if (direntry->name[0] != '.'){
- strcat(simasel->dir, direntry->name);
- strcat(simasel->dir, "/");
+ if (simasel->img) {
+ IMB_freeImBuf(simasel->img);
}
- else {
- if (direntry->name[1] == '.'){
- imadir_parent(simasel);
- }
+ if(simasel->pupmenu) {
+ MEM_freeN(simasel->pupmenu);
+ simasel->pupmenu = NULL;
}
-
- clear_ima_dir(simasel);
-}
-
-void check_imasel_copy(SpaceImaSel *simasel)
-{
-
- /* WATCH IT: also used when reading blender file */
- /* initialize stuff, malloc, etc */
- simasel->first_sel_ima = 0;
- simasel->hilite_ima = 0;
- simasel->firstdir = 0;
- simasel->firstfile = 0;
- simasel->cmap = 0;
- clear_ima_dir(simasel);
-
- // simasel->cmap= IMB_loadiffmem((int*)datatoc_cmap_tga, IB_rect|IB_cmap);
- simasel->cmap= IMB_ibImageFromMemory((int *)datatoc_cmap_tga, datatoc_cmap_tga_size, IB_rect|IB_cmap);
-}
-
-void free_imasel(SpaceImaSel *simasel)
-{
- /* do not free imasel itself */
-
- clear_ima_dir(simasel);
- IMB_freeImBuf(simasel->cmap);
}
diff --git a/source/blender/src/interface_draw.c b/source/blender/src/interface_draw.c
index 2af1892de1c..1a64f28d982 100644
--- a/source/blender/src/interface_draw.c
+++ b/source/blender/src/interface_draw.c
@@ -2431,3 +2431,33 @@ void ui_draw_but(uiBut *but)
}
}
+void ui_dropshadow(rctf *rct, float radius, float aspect, int select)
+{
+ float rad;
+ float a;
+ char alpha= 2;
+
+ glEnable(GL_BLEND);
+
+ if(radius > (rct->ymax-rct->ymin-10.0f)/2.0f)
+ rad= (rct->ymax-rct->ymin-10.0f)/2.0f;
+ else
+ rad= radius;
+
+ if(select) a= 12.0f*aspect; else a= 12.0f*aspect;
+ for(; a>0.0f; a-=aspect) {
+ /* alpha ranges from 2 to 20 or so */
+ glColor4ub(0, 0, 0, alpha);
+ alpha+= 2;
+
+ gl_round_box(GL_POLYGON, rct->xmin - a, rct->ymin - a, rct->xmax + a, rct->ymax-10.0f + a, rad+a);
+ }
+
+ /* outline emphasis */
+ glEnable( GL_LINE_SMOOTH );
+ glColor4ub(0, 0, 0, 100);
+ gl_round_box(GL_LINE_LOOP, rct->xmin-0.5f, rct->ymin-0.5f, rct->xmax+0.5f, rct->ymax+0.5f, radius);
+ glDisable( GL_LINE_SMOOTH );
+
+ glDisable(GL_BLEND);
+}
diff --git a/source/blender/src/interface_icons.c b/source/blender/src/interface_icons.c
index d257f2f37f8..610ad09ca34 100644
--- a/source/blender/src/interface_icons.c
+++ b/source/blender/src/interface_icons.c
@@ -90,11 +90,6 @@
#include "datatoc.h"
#include "mydevice.h"
-/* OpenGL textures have to be size 2n+2 x 2m+2 for some n,m */
-/* choose ICON_RENDERSIZE accordingly */
-#define ICON_RENDERSIZE 32
-#define ICON_MIPMAPS 8
-
#define ICON_IMAGE_W 512
#define ICON_IMAGE_H 256
@@ -105,52 +100,60 @@
#define ICON_GRID_W 15
#define ICON_GRID_H 16
+typedef struct IconImage {
+ int w;
+ int h;
+ unsigned int *rect;
+} IconImage;
+
typedef struct DrawInfo {
int w;
int h;
- int rw;
- int rh;
- VectorDrawFunc drawFunc; /* If drawFunc is defined then it is a vector icon, otherwise use rect */
float aspect;
- unsigned int *rect;
+ VectorDrawFunc drawFunc; /* If drawFunc is defined then it is a vector icon, otherwise use rect */
+ IconImage* icon;
} DrawInfo;
-
/* ******************* STATIC LOCAL VARS ******************* */
/* static here to cache results of icon directory scan, so it's not
* scanning the filesystem each time the menu is drawn */
static struct ListBase iconfilelist = {0, 0};
+static int preview_render_size(int miplevel);
+
/* **************************************************** */
static void def_internal_icon(ImBuf *bbuf, int icon_id, int xofs, int yofs)
{
Icon *new_icon = NULL;
+ IconImage *iimg = NULL;
DrawInfo *di;
int y = 0;
new_icon = MEM_callocN(sizeof(Icon), "texicon");
new_icon->obj = 0; /* icon is not for library object */
- new_icon->type = 0;
- new_icon->changed = 0;
-
+ new_icon->type = 0;
di = MEM_callocN(sizeof(DrawInfo), "drawinfo");
di->drawFunc = 0;
di->w = ICON_DEFAULT_HEIGHT;
di->h = ICON_DEFAULT_HEIGHT;
- di->rw = ICON_DEFAULT_HEIGHT;
- di->rh = ICON_DEFAULT_HEIGHT;
di->aspect = 1.0f;
- di->rect = MEM_mallocN(ICON_DEFAULT_HEIGHT*ICON_DEFAULT_HEIGHT*sizeof(unsigned int), "icon_rect");
+ iimg = MEM_mallocN(sizeof(IconImage), "icon_img");
+ iimg->rect = MEM_mallocN(ICON_DEFAULT_HEIGHT*ICON_DEFAULT_HEIGHT*sizeof(unsigned int), "icon_rect");
+ iimg->w = ICON_DEFAULT_HEIGHT;
+ iimg->h = ICON_DEFAULT_HEIGHT;
+
/* Here we store the rect in the icon - same as before */
for (y=0; y<ICON_DEFAULT_HEIGHT; y++) {
- memcpy(&di->rect[y*ICON_DEFAULT_HEIGHT], &bbuf->rect[(y+yofs)*512+xofs], ICON_DEFAULT_HEIGHT*sizeof(int));
+ memcpy(&iimg->rect[y*ICON_DEFAULT_HEIGHT], &bbuf->rect[(y+yofs)*512+xofs], ICON_DEFAULT_HEIGHT*sizeof(int));
}
+ di->icon = iimg;
+
new_icon->drawinfo_free = BIF_icons_free_drawinfo;
new_icon->drawinfo = di;
@@ -166,17 +169,14 @@ static void def_internal_vicon( int icon_id, VectorDrawFunc drawFunc)
new_icon->obj = 0; /* icon is not for library object */
new_icon->type = 0;
- new_icon->changed = 0;
-
+
di = MEM_callocN(sizeof(DrawInfo), "drawinfo");
di->drawFunc =drawFunc;
di->w = ICON_DEFAULT_HEIGHT;
di->h = ICON_DEFAULT_HEIGHT;
- di->rw = ICON_DEFAULT_HEIGHT;
- di->rh = ICON_DEFAULT_HEIGHT;
di->aspect = 1.0f;
- di->rect = NULL;
-
+ di->icon = NULL;
+
new_icon->drawinfo_free = 0;
new_icon->drawinfo = di;
@@ -693,7 +693,10 @@ void BIF_icons_free_drawinfo(void *drawinfo)
if (di)
{
- MEM_freeN(di->rect);
+ if (di->icon) {
+ MEM_freeN(di->icon->rect);
+ MEM_freeN(di->icon);
+ }
MEM_freeN(di);
}
}
@@ -705,11 +708,9 @@ static DrawInfo *icon_create_drawinfo()
di = MEM_callocN(sizeof(DrawInfo), "di_icon");
di->drawFunc = 0;
- di->w = 16;
- di->h = 16;
- di->rw = ICON_RENDERSIZE;
- di->rh = ICON_RENDERSIZE;
- di->rect = 0;
+ di->w = ICON_DEFAULT_HEIGHT;
+ di->h = ICON_DEFAULT_HEIGHT;
+ di->icon = NULL;
di->aspect = 1.0f;
return di;
@@ -771,7 +772,7 @@ void BIF_icons_init(int first_dyn_id)
init_internal_icons();
}
-static void icon_copy_rect(ImBuf *ibuf, RenderInfo *ri)
+static void icon_copy_rect(ImBuf *ibuf, unsigned int w, unsigned int h, unsigned int *rect)
{
struct ImBuf *ima;
unsigned int *drect, *srect;
@@ -789,19 +790,19 @@ static void icon_copy_rect(ImBuf *ibuf, RenderInfo *ri)
return;
if (ima->x > ima->y) {
- scaledx = (float)ri->pr_rectx;
- scaledy = ( (float)ima->y/(float)ima->x )*(float)ri->pr_rectx;
+ scaledx = (float)w;
+ scaledy = ( (float)ima->y/(float)ima->x )*(float)w;
}
else {
- scaledx = ( (float)ima->x/(float)ima->y )*(float)ri->pr_recty;
- scaledy = (float)ri->pr_recty;
+ scaledx = ( (float)ima->x/(float)ima->y )*(float)h;
+ scaledy = (float)h;
}
ex = (short)scaledx;
ey = (short)scaledy;
- dx = (ri->pr_rectx - ex) / 2;
- dy = (ri->pr_recty - ey) / 2;
+ dx = (w - ex) / 2;
+ dy = (h - ey) / 2;
IMB_scalefastImBuf(ima, ex, ey);
@@ -810,61 +811,66 @@ static void icon_copy_rect(ImBuf *ibuf, RenderInfo *ri)
IMB_rect_from_float(ima);
srect = ima->rect;
- drect = ri->rect;
+ drect = rect;
- drect+= dy*ri->pr_rectx+dx;
+ drect+= dy*w+dx;
for (;ey > 0; ey--){
memcpy(drect,srect, ex * sizeof(int));
- drect += ri->pr_rectx;
+ drect += w;
srect += ima->x;
}
IMB_freeImBuf(ima);
}
+static void icon_create_mipmap(struct PreviewImage* prv_img, int miplevel)
+{
+ unsigned int size = preview_render_size(miplevel);
+
+ if (!prv_img) {
+ printf("Error: requested preview image does not exist");
+ }
+ if (!prv_img->rect[miplevel]) {
+ prv_img->w[miplevel] = size;
+ prv_img->h[miplevel] = size;
+ prv_img->changed[miplevel] = 1;
+ prv_img->rect[miplevel] = MEM_callocN(size*size*sizeof(unsigned int), "prv_rect");
+ }
+}
+
/* create single icon from jpg, png etc. */
-static void icon_from_image(Image *img, RenderInfo *ri)
+static void icon_from_image(Image *img, int miplevel)
{
- unsigned int pr_size = ri->pr_rectx*ri->pr_recty*sizeof(unsigned int);
+ unsigned int pr_size;
+ short image_loaded = 0;
+ struct ImBuf* ibuf=NULL;
+ PreviewImage* pi;
/* img->ok is zero when Image cannot load */
if (img==NULL || img->ok==0)
return;
-
- if (!ri->rect) {
- ri->rect= MEM_callocN(pr_size, "butsrect");
- memset(ri->rect, 0x00, pr_size);
+
+ /* elubie: this needs to be changed: here image is always loaded if not
+ already there. Very expensive for large images. Need to find a way to
+ only get existing ibuf */
+ ibuf = BKE_image_get_ibuf(img, NULL);
+ if(ibuf==NULL || ibuf->rect==NULL) {
+ return;
}
- /* we only load image if there's no preview saved already ...
- always loading and reducing images is too expensive */
- /* new rule: never read images, so icons get created while user works,
- not always on first use of a menu */
- if(!img->preview) {
- ImBuf *ibuf;
- if(img->ok!=IMA_OK_LOADED) {
- return;
- }
- ibuf= BKE_image_get_ibuf(img, NULL);
- icon_copy_rect(ibuf, ri);
-
- /* now copy the created preview to the DNA struct to be saved in file */
- img->preview = MEM_callocN(sizeof(PreviewImage), "img_prv");
- if (img->preview) {
- printf("created image prv\n");
- img->preview->w = ri->pr_rectx;
- img->preview->h = ri->pr_recty;
- img->preview->rect = MEM_callocN(pr_size, "prv_rect");
- memcpy(img->preview->rect, ri->rect, pr_size);
- }
- }
- else {
- unsigned int img_prv_size = img->preview->w*img->preview->h*sizeof(unsigned int);
- if (!img->preview->rect || img_prv_size != pr_size) {
- printf("Missing preview or wrong preview size!\n");
- return;
- }
- memcpy(ri->rect, img->preview->rect, pr_size);
+ pi = BKE_previewimg_get((ID*)img);
+
+ if(!pi) {
+ printf("preview image could'nt be allocated");
+ return;
}
+ /* we can only create the preview rect here, since loading possibly deallocated
+ old preview */
+ icon_create_mipmap(pi, miplevel);
+
+ pr_size = img->preview->w[miplevel]*img->preview->h[miplevel]*sizeof(unsigned int);
+
+ image_loaded = 1;
+ icon_copy_rect(ibuf, img->preview->w[miplevel], img->preview->h[miplevel], img->preview->rect[miplevel]);
}
static void set_alpha(char* cp, int sizex, int sizey, char alpha)
@@ -879,27 +885,36 @@ static void set_alpha(char* cp, int sizex, int sizey, char alpha)
/* only called when icon has changed */
/* only call with valid pointer from BIF_icon_draw */
-static void icon_set_image(ID *id, DrawInfo *di)
+static void icon_set_image(ID *id, DrawInfo *di, PreviewImage* prv_img, int miplevel)
{
RenderInfo ri;
-
- if (!di) return;
-
- if (!di->rect)
- di->rect = MEM_callocN(di->rw*di->rh*sizeof(unsigned int), "laprevrect");
+ unsigned int pr_size = 0;
+
+ if (!di) return;
- ri.curtile= 0;
- ri.tottile= 0;
- ri.rect = NULL;
- ri.pr_rectx = di->rw;
- ri.pr_recty = di->rh;
+ if (!prv_img) {
+ printf("No preview image for this ID: %s\n", id->name);
+ return;
+ }
/* no drawing (see last parameter doDraw, just calculate preview image
- hopefully small enough to be fast */
if (GS(id->name) == ID_IM)
- icon_from_image((struct Image*)id, &ri);
- else {
+ icon_from_image((struct Image*)id, miplevel);
+ else {
+ /* create the preview rect */
+ icon_create_mipmap(prv_img, miplevel);
+
+ ri.curtile= 0;
+ ri.tottile= 0;
+ ri.rect = NULL;
+ ri.pr_rectx = prv_img->w[miplevel];
+ ri.pr_recty = prv_img->h[miplevel];
+
+ pr_size = ri.pr_rectx*ri.pr_recty*sizeof(unsigned int);
+
BIF_previewrender(id, &ri, NULL, PR_ICON_RENDER);
+
/* world is rendered with alpha=0, so it wasn't displayed
this could be render option for sky to, for later */
if (GS(id->name) == ID_WO) {
@@ -909,25 +924,74 @@ static void icon_set_image(ID *id, DrawInfo *di)
Material* mat = (Material*)id;
if (mat->mode & MA_HALO) {
set_alpha( (char*) ri.rect, ri.pr_rectx, ri.pr_recty, 255);
- }
+ }
+ }
+
+ if (ri.rect) {
+ memcpy(prv_img->rect[miplevel], ri.rect, pr_size);
+
+ /* and clean up */
+ MEM_freeN(ri.rect);
+ ri.rect = 0;
}
}
+}
- /* and copy the image into the icon */
- if (ri.rect) {
- memcpy(di->rect, ri.rect,di->rw*di->rh*sizeof(unsigned int));
+static void icon_draw_rect(float x, float y, int w, int h, float aspect, int rw, int rh, unsigned int *rect)
+{
+ ui_rasterpos_safe(x, y, aspect);
+
+ if(w<1 || h<1) {
+ printf("what the heck!\n");
+ }
+ /* rect contains image in 'rendersize', we only scale if needed */
+ else if(rw!=w && rh!=h) {
+ ImBuf *ima;
+ if(w>2000 || h>2000) { /* something has gone wrong! */
+ printf("insane icon size w=%d h=%d\n",w,h);
+ return;
+ }
+ /* first allocate imbuf for scaling and copy preview into it */
+ ima = IMB_allocImBuf(rw, rh, 32, IB_rect, 0);
+ memcpy(ima->rect, rect, rw*rh*sizeof(unsigned int));
+
+ /* scale it */
+ IMB_scaleImBuf(ima, w, h);
+ glDrawPixels(w, h, GL_RGBA, GL_UNSIGNED_BYTE, ima->rect);
+
+ IMB_freeImBuf(ima);
+ }
+ else
+ glDrawPixels(w, h, GL_RGBA, GL_UNSIGNED_BYTE, rect);
+}
- /* and clean up */
- MEM_freeN(ri.rect);
- ri.rect = 0;
+/* Render size for preview images at level miplevel */
+static int preview_render_size(int miplevel)
+{
+ switch (miplevel) {
+ case 0: return 32;
+ case 1: return PREVIEW_DEFAULT_HEIGHT;
}
+ return 0;
}
-void BIF_icon_draw_aspect(float x, float y, int icon_id, float aspect)
+/* Drawing size for preview images at level miplevel */
+static int preview_size(int miplevel)
+{
+ switch (miplevel) {
+ case 0: return ICON_DEFAULT_HEIGHT;
+ case 1: return PREVIEW_DEFAULT_HEIGHT;
+ }
+ return 0;
+}
+
+
+static void icon_draw_mipmap(float x, float y, int icon_id, float aspect, int miplevel, int nocreate)
{
Icon *icon = NULL;
DrawInfo *di = NULL;
-
+ int draw_size = preview_size(miplevel);
+
icon = BKE_icon_get(icon_id);
if (!icon) {
@@ -939,65 +1003,61 @@ void BIF_icon_draw_aspect(float x, float y, int icon_id, float aspect)
if (!di) {
di = icon_create_drawinfo();
-
- icon->changed = 1;
+
icon->drawinfo = di;
icon->drawinfo_free = BIF_icons_free_drawinfo;
}
di->aspect = aspect;
/* scale width and height according to aspect */
- di->w = (int)(ICON_DEFAULT_HEIGHT/di->aspect + 0.5f);
- di->h = (int)(ICON_DEFAULT_HEIGHT/di->aspect + 0.5f);
+ di->w = (int)(draw_size/di->aspect + 0.5f);
+ di->h = (int)(draw_size/di->aspect + 0.5f);
if (di->drawFunc) {
/* vector icons use the uiBlock transformation, they are not drawn
with untransformed coordinates like the other icons */
di->drawFunc(x, y, ICON_DEFAULT_HEIGHT, ICON_DEFAULT_HEIGHT, 1.0f);
+ }
+ else if (di->icon) {
+ /* it is a builtin icon */
+ if (!di->icon->rect) return; /* something has gone wrong! */
+
+ icon_draw_rect(x,y,di->w, di->h, di->aspect, di->icon->w, di->icon->h, di->icon->rect);
}
else {
- if (icon->changed) /* changed only ever set by dynamic icons */
- {
- waitcursor(1);
- icon_set_image((ID*)icon->obj, icon->drawinfo);
- icon->changed = 0;
- waitcursor(0);
- }
-
- if (!di->rect) return; /* something has gone wrong! */
-
- ui_rasterpos_safe(x, y, di->aspect);
-
- if(di->w<1 || di->h<1) {
- printf("what the heck!\n");
- }
- /* di->rect contains image in 'rendersize', we only scale if needed */
- else if(di->rw!=di->w && di->rh!=di->h) {
- ImBuf *ima;
- if(di->w>2000 || di->h>2000) { /* something has gone wrong! */
- printf("insane icon size di->w %d di->h %d\n",di->w,di->h);
- return;
+ PreviewImage* pi = BKE_previewimg_get((ID*)icon->obj);
+
+ if (pi) {
+ if (!nocreate && pi->changed[miplevel]) /* changed only ever set by dynamic icons */
+ {
+ waitcursor(1);
+ /* create the preview rect if necessary */
+ icon_set_image((ID*)icon->obj, icon->drawinfo, pi, miplevel);
+ pi->changed[miplevel] = 0;
+ waitcursor(0);
}
- /* first allocate imbuf for scaling and copy preview into it */
- ima = IMB_allocImBuf(di->rw, di->rh, 32, IB_rect, 0);
- memcpy(ima->rect, di->rect, di->rw*di->rh*sizeof(unsigned int));
- /* scale it */
- IMB_scaleImBuf(ima, di->w, di->h);
- glDrawPixels(di->w, di->h, GL_RGBA, GL_UNSIGNED_BYTE, ima->rect);
+ if (!pi->rect[miplevel]) return; /* something has gone wrong! */
- IMB_freeImBuf(ima);
+ icon_draw_rect(x,y,di->w, di->h, di->aspect, pi->w[miplevel], pi->h[miplevel], pi->rect[miplevel]);
}
- else
- glDrawPixels(di->w, di->h, GL_RGBA, GL_UNSIGNED_BYTE, di->rect);
}
}
+void BIF_icon_draw_aspect(float x, float y, int icon_id, float aspect)
+{
+ icon_draw_mipmap(x,y,icon_id, aspect, PREVIEW_MIPMAP_ZERO, 0);
+}
+
void BIF_icon_draw(float x, float y, int icon_id)
{
BIF_icon_draw_aspect(x, y, icon_id, 1.0f);
}
+void BIF_icon_draw_preview(float x, float y, int icon_id, int nocreate)
+{
+ icon_draw_mipmap(x,y,icon_id, 1.0f, PREVIEW_MIPMAP_LARGE, nocreate);
+}
void BIF_icon_draw_aspect_blended(float x, float y, int icon_id, float aspect, int shade)
{
diff --git a/source/blender/src/prvicons.c b/source/blender/src/prvicons.c
new file mode 100644
index 00000000000..6222090705a
--- /dev/null
+++ b/source/blender/src/prvicons.c
@@ -0,0 +1,436 @@
+/* DataToC output of file <prvicons> */
+
+int datatoc_prvicons_size= 13732;
+char datatoc_prvicons[]= {
+137, 80, 78, 71,
+ 13, 10, 26, 10, 0, 0, 0, 13, 73, 72, 68, 82, 0, 0, 0,192, 0, 0, 0,192, 8, 6, 0, 0, 0, 82,220,108, 7, 0, 0, 0,
+ 6, 98, 75, 71, 68, 0, 0, 0, 0, 0, 0,249, 67,187,127, 0, 0, 0, 9,112, 72, 89,115, 0, 0, 11, 19, 0, 0, 11, 19, 1,
+ 0,154,156, 24, 0, 0, 0, 7,116, 73, 77, 69, 7,215, 8, 27, 17, 57, 33, 43,142, 73,203, 0, 0, 0, 29,116, 69, 88,116, 67,
+111,109,109,101,110,116, 0, 67,114,101, 97,116,101,100, 32,119,105,116,104, 32, 84,104,101, 32, 71, 73, 77, 80,239,100, 37,110,
+ 0, 0, 32, 0, 73, 68, 65, 84,120,218,237,125,121,124, 84,213,249,254,115,238,189, 51,147,201,158, 12, 73, 72,216, 3,200, 98,
+ 88, 69, 66, 38, 65, 16, 20,165, 40,213,162, 32, 45,138,203, 79,176,223, 42,180,110, 72,235,190, 97, 91, 91, 21,181,149,182, 90,
+ 20, 42, 10, 66, 80,164, 34, 59,146, 5,194, 30, 18, 8, 75, 2,201,144,144,201, 62, 73,102,189,247,158,243,251, 35,235, 36, 51,
+217,200,100, 38,229, 62,159,207,124,146,123,239,153, 59,207, 61,247,125,207,121,223,247,156,243, 30, 64,129, 2, 5, 10, 20, 40,
+ 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2,
+ 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,
+160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5,
+ 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160,
+ 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,160, 64,129, 2, 5, 10, 20, 40, 80,208, 18, 36, 41, 41,105,
+180, 32, 8,143, 16, 66, 72,119,223,156, 49, 22, 46,203,242,112,198,216,203, 41, 41, 41,251, 60,241, 0,189,157,191, 2,239, 43,
+192, 61, 49, 49, 49, 27,230,204,153,227,215,157, 55,206,206,206,198,169, 83,167, 16, 25, 25, 9,131,193, 64, 37, 73,154,150,146,
+146,146,226, 1, 5,232,213,252, 21,120, 23, 2, 0, 68, 71, 71,219, 23, 46, 92,216,109, 2,180,105,211, 38, 24, 12, 6, 60,250,
+232,163,224, 56, 14, 7, 15, 30,228, 50, 51, 51, 15, 36, 38, 38, 38,164,166,166,102,116,247, 67,244,118,254, 10,188, 7,174,187,
+111, 40, 73, 18,214,175, 95,143, 5, 11, 22,160,111,223,190,240,247,247, 71, 98, 98, 34,226,226,226, 56,149, 74,149,174,215,235,
+ 39,250,114,133,244,118,254, 10,188,172, 0, 6,131, 1,193,193,193,136,136,136,128, 32, 8,208,106,181,208,106,181,208,235,245,
+ 24, 57,114, 36,167, 86,171, 51,244,122,125,156,175, 86, 72,111,231,175,192,203, 10, 80, 88, 88, 8,157, 78,215,120,172,209,104,
+ 26,133, 40, 49, 49, 17,195,135, 15,231,213,106,245,137,132,132,132, 27,124,177, 66,122, 59,127, 5, 94, 86,128,192,192, 64, 88,
+173, 86,167,115,254,254,254,141,159,164,164, 36,196,198,198, 10,126,126,126, 89,122,189, 62,214,215, 42,164,183,243, 87,224,101,
+ 5,208,233,116, 48,153, 76,173,206, 55,180,162, 90,173, 22, 73, 73, 73, 24, 56,112,160, 74,163,209,156,213,235,245, 3,124,169,
+ 66,122, 59,127, 5,157,131,208,221, 55,140,138,138, 66, 77, 77, 13,172, 86, 43,180, 90, 45, 0,160,170,170, 10,165,165,165, 40,
+ 47, 47, 71,105,105, 41, 44, 22, 11, 6, 15, 30, 12, 81, 20,213, 87,175, 94, 61,175,215,235,135,164,165,165, 21,251, 66,133,244,
+118,254, 10,188,172, 0,106,181, 26,227,199,143, 71, 78, 78, 14,116, 58, 29, 14, 28, 56,128,130,130, 2,196,198,198, 34, 42, 42,
+ 10, 67,135, 14, 5,207,243, 72, 77, 77,133,209,104,132, 40,138,126, 26,141, 38, 79,175,215, 15, 74, 75, 75, 43,245,118,133,244,
+118,254, 10,188,172, 0, 0, 48,109,218, 52,124,250,233,167, 16, 69, 17,143, 63,254, 56,102,206,156, 9,181, 90,237, 84,102,209,
+162, 69, 48,153, 76, 88,183,110, 29,182,108,217,162,165,148,190, 9,224, 9, 0,204,219,149,210,219,249, 43,240,162, 15, 0, 0,
+ 9, 9, 9, 8, 12, 12,196, 71, 31,125,132,217,179,103,183, 18,158, 6,132,132,132,224,201, 39,159,132, 70,163, 97, 86,171,117,
+108,104,104,104,127, 0,196,219,149,210,219,249, 43,240,178, 2, 4, 5, 5, 97,205,154, 53,136,137,137,233, 80,249, 33, 67,134,
+ 72, 86,171,213,204,243,252,253,190, 32, 64,189,157,191, 2, 47, 43, 0, 0, 8, 66,199,173, 43, 63, 63, 63, 70, 41,149, 24, 99,
+ 26, 95, 17,160,222,206, 95,129,151, 21,160,139,144,123,121,125,202,138, 72, 41, 10,208, 37, 16, 66,100, 66, 72,175, 21,160,222,
+206,255,122,133,208, 19, 63, 98,178,216,193, 24,131, 74,224, 17,160, 81,185,109, 61, 25, 99, 50,122,111, 20,165,183,243, 87, 20,
+192, 19,200, 45,174,194,152,103, 62, 5, 0, 68,135, 5,226,252,234, 37,224,185,122, 51,153, 81, 56,142,252, 11,183, 71, 92,225,
+ 39,223, 22, 56, 50, 88,173,213,234, 99,111,136,134, 64,254, 25,249,155,244,139,158,230,166, 82,185, 85, 70,136,162,216,217, 30,
+128, 2,160,138, 15,160, 40,128, 19, 62, 63,112,186,241,255,171,149,181,248,241,100, 30,126, 54,113, 40, 0,128,154,174,192,126,
+124, 61,146,194,192, 35, 76, 51, 28,192,112, 0,183, 17,137,255,216,155,194,223,145,235, 45,148,132, 1,104, 48,129,148, 30, 64,
+241, 1,234,109, 2,202,240,159,159,178,157,206,125,113, 32,171,241,127, 90,118,190,213,119, 24, 80, 30,190, 60,165,192,155,194,
+223,197,251, 80,197, 9, 86, 20,192, 9, 59, 79, 93,194,213, 42, 51,180,234,166,142,230,135, 19,121, 40,173,182,212, 41, 72,217,
+ 5,184,208,128, 19,189,169, 2,155, 41, 1,173,247, 1, 20, 40, 10,224,220,218,191,255,240, 76, 52, 44, 89, 23,101,138, 13, 41,
+103,234, 36,166,212,101, 15,112,220,215, 43, 77, 20, 69,167, 15, 0, 13,165, 20, 0,244, 0,120, 69,172, 20, 5, 64,105,181, 5,
+255, 61,158,139, 65, 17, 33, 88,116, 75, 28,102,196, 13,106,230, 23,100,213,247, 0, 46, 20,128,178,227,189,173, 18, 25, 99, 0,
+ 16, 7,160, 76,241, 1, 20, 39, 24, 0,176, 33,229, 12, 68,153,226,161,105, 55,130, 16,224,161,105, 99,176,231,116, 62, 0,224,
+236,149,114,100,100,102, 97,148,189,166,213,247,204,140,157, 0,128,146,143,167, 7,242,212, 54, 7,192, 72, 70,137,131,227,113,
+ 90,148,232,145,168,223, 30, 54,250,168, 2,252, 4,160, 90, 17, 41,165, 7,104,108,229, 57, 66,240,224,180,186,229,179,115, 39,
+ 13, 67, 88, 64, 83,226,134,181,123, 91,155,250,162,204, 44,187,114,228, 75,229,171,227,159,225,101, 91, 49, 24,190, 2,195,171,
+132,176,183, 25,101,219, 4,142,228, 85,172, 78, 88,234,139, 21,233,112, 56,202, 25, 99,134,122,103, 88,193,245,172, 0, 71,115,
+139,113,246, 74, 57,102,142, 25,132,254,225, 65, 0, 0,141,138,199,130,196, 81,141,101, 54,159, 42,133, 85,118, 54,151,171,172,
+180,224, 23,113,170,117, 0,121, 23, 64,128,139, 91,251, 51,176, 79,202, 62, 72, 88,229,131,117, 25, 98,179,217,250,195,247,166,
+151, 40,232,105, 5, 88,187,191, 46,246,191,120,250, 24,167,243, 15, 79,111, 74,166, 80,227, 96,216, 86,230, 60,219, 82, 23,192,
+ 15, 35,192,130,246,238, 79, 8,123,166,236,189, 41,163,188, 85,105, 42,149,170, 85, 40,149, 16, 2, 74,169, 77, 81,128,235, 92,
+ 1, 44,118, 17,223,164,159,131, 46, 72,139,187,110, 26,234,116,109,236,160, 72,140, 27, 28,217,228, 39, 24, 7, 57,147, 33, 16,
+ 24, 96, 7,240, 79, 2,242, 75, 2,242, 75, 6, 28,112, 37,131,132,195,115,222,170,180,102,209,159, 70,225,231, 56, 14, 42,149,
+234, 40,234,162, 64,202,104,240,245,170, 0, 91,143, 92, 64,181,213,142, 7, 18, 71, 65, 45,180,142, 8, 62,220,172, 87, 72,175,
+ 14,199,101, 91,147,165, 67, 41,236,162,204,238,214, 45, 59,180, 36,124, 89,250,134,240,101,233, 27,116, 21,126,183, 1,200,105,
+221, 13,224,198,107, 17, 96, 15, 33,166,222, 7, 96, 0, 84,138,120, 93,135, 10,208, 16,251, 95, 60,205,117,238,168,249,250,145,
+240, 19,184,250,232, 9,193,134,226,129,141,215, 14, 92, 52,255, 43,250,119,135,247, 56,201,249,171,251, 37, 66, 88,178,139,216,
+139, 79,229,229,169,207,205, 43,212,127, 72,125,221,106, 20, 17,187,142, 20,224, 82,137, 9, 7,207, 26, 48, 49, 54, 10,113, 3,
+ 35, 92,150, 9, 11,240,195, 93,195,154,150, 24,126,109, 28, 8,153, 17, 88, 37, 88, 95,218,102,220,233, 70,188,170, 92,156,243,
+243,149, 74,164,148,130, 82, 10, 73,146, 56, 0, 13,221,139, 31,234,204, 57, 5, 62,140,110, 29, 7,248,226, 64, 22, 24, 3,146,
+ 70, 14, 64,102,126,137,219,114, 19,131, 42,241, 13,234, 82,142, 92,117,248, 97,127,101, 36, 2,107, 11, 47, 24,107, 36,171,171,
+242,140,161,159,139,211, 62,149,129,161,190, 7, 16,209, 52, 16,102, 82,196,235, 58, 82, 0,202, 24,214,255, 84,103,254,172,254,
+239, 81,172,254,239,209, 54, 74,107,157,142, 54, 24, 7,226, 94,114,165,202,221,130, 18, 2, 50,136,181, 30, 96,205,242, 86,165,
+ 53, 68,128,154,251, 18,140, 49,112, 28, 39,214,215,169,168,136,214,117,166, 0,187, 78, 93, 70, 97, 69, 45,166,142, 26,128,219,
+199, 14,118, 95, 80,118,192,126,116, 45, 14,155,194,177,187, 50, 10, 0,240, 99,121, 95,220,168,209, 88, 40,165,173,166, 19,151,
+175,142, 15,102, 96,183,182,234, 21, 0,175,231,234, 87,169, 84, 78, 74,192,113,156, 67, 49,123,174, 83, 5,104,112,126, 95,186,
+ 79,143,164,145,253,221,150,147,138, 78,192,106, 60,143,139,186, 64,236, 62, 86,167, 0, 14,198,225, 44, 63,108, 24, 33, 57,178,
+ 11,211,226, 9,198, 16,220,178,195,225,101,124,233, 11, 21,216,208, 27,168, 84, 42,155, 90,173,110,112,128, 21, 92, 79, 78,112,
+121,141, 21,219,143,231, 98, 72,100, 8, 18, 71,244,111,219, 84,170,159, 1, 58,204,191, 22, 55, 7, 87, 52,158, 63, 45,247, 31,
+ 76,235,167, 84, 54,160,236,195,201, 51, 24,195, 75, 46,140,162, 45, 97,191, 59,116,217,135,236,255, 82, 65, 16,120, 40, 19,225,
+174,207, 30,224,171,212,179,112, 72, 50, 22,221,114, 35,218,219,169,171,249, 26,128, 95, 70,229,227, 72,117, 56, 0, 32,207, 22,
+ 36,124,241,127,250, 79,110,139,170,120,141,112, 40,231, 25,110,167, 12,207,160,117, 40,209,194,113,228, 89, 95,170, 68,158,231,
+ 3,120,158,175, 97,140, 29,135, 50, 23,232,250,235, 1,214,238, 63, 13,142, 16, 44,186,165,253,125, 35,154,175, 2,251,121, 68,
+ 33,252, 57,169,241,120,111,109,255, 49, 60,193, 55, 28,195, 62, 6,252,158,180, 22,126, 10, 66, 30, 14,123, 50, 45,223,199,234,
+145, 17, 66,168, 39, 54,234, 83,224,163, 61, 64, 65, 89, 53,118,158,186,132,242, 26, 43,178, 13,101,232, 23, 30,136, 31, 79,230,
+ 1, 0,126, 54,113, 40, 98,194, 2, 91, 75,137,100, 3,173, 42, 64,165,164,198,119,165,117,243,128, 6,105, 45, 56,107,174, 51,
+241,183,148,246,199,232,128,186, 25,197,183,134,149, 96,160,159,197,201,125, 32,192,178,240,167,210, 55,249, 82, 5,138,162,216,
+ 16, 2,149, 91,154,112, 10,254,135, 21, 32,203, 80,134,101,159,237,110, 60, 46,172,168,109, 60, 30,214, 55,204,165, 2,208,242,
+ 92,128, 81, 20,219,253,240,252,197,113,173,174, 87, 75,170,198,243,159,141,202,104,174, 0, 57,132,224,255,133, 63,117, 40,181,
+ 59, 5,247, 90,215, 6, 55, 68,128, 24, 99,168,239, 1, 20, 5,184, 94, 20, 32,126, 88, 52,118,252, 97,190,203,107, 99, 7,185,
+ 30, 5,230,130,251, 65, 59,247, 3,140,112,200,216, 62,185,166,222,129,228,177,230,235, 31,109,135,207,228,173, 11, 12,208,156,
+126,112, 28, 25, 30,161,178, 15, 25, 27,100,178, 1,200, 97,132,238,235,243, 84,198, 94, 79,181,222,157, 77,141, 34, 73, 82,171,
+180,137,132, 16, 48,198,168, 44,203, 65,138, 72, 93, 39, 10,160, 11,210,226,150,209,157,219, 28,133,104, 67, 33,104, 39, 32, 4,
+192,173,131,155,206,127,191,245, 59, 57,220,116,225, 66,126,102,254,174, 63,236, 48,125,212,147,209,148,206, 78,140,115,151, 51,
+ 84,201, 12,119, 29, 59,193,221,132,222, 46, 64,138, 2,244,214, 30,192,100, 50, 9, 25, 25,222,219,255,217,100, 50,241,132, 16,
+ 42,203,178,220,197,239,247,106,254, 10,188,171, 0,198,226,226,226, 83,171, 86,173,226,237,118,123, 52, 99, 76,141,186,176, 30,
+234, 77, 17,214,204, 36, 97,132,144,198,255, 91, 94,115,119,189,197,189, 90,150,101,178, 44,203,146, 36,149,212, 59,145,157, 53,
+127,122, 59,127, 5, 94, 68,243,184, 53,167,211,233,150, 3,232,139,166, 44,103, 50, 99, 76, 34,132,200,140, 49,153, 16, 34, 53,
+ 59, 71,155, 93,107, 56, 47, 19, 66,164,250, 4, 81,114,195, 53, 66,136, 76, 41,149, 90, 28,203, 13,118, 51,165, 84,146,101, 89,
+ 98,140, 89,204,102,243,149,174,154,115,189,156,191, 2, 47, 43, 0, 9, 12, 12,140,230, 56, 78, 77, 8, 97,245, 19,189, 26, 91,
+185,134, 86,176,249,113,125,232,143, 1,128,195,225,112,106, 65, 9, 33,172,217,167,161, 44, 44, 22,139,211, 61, 56,142, 99,132,
+ 16, 86, 89, 89,201,234,133,182,171, 51, 41,123, 59,127, 5, 94, 86, 0, 87,199, 29, 5,243,209,231,233,109,252, 21,244,180,192,
+ 36, 37, 37,141, 22, 4,225, 17, 79, 12,227, 51,198,194,101, 89, 30,206, 24,123, 57, 37, 37,101,159, 39, 30, 64,225,175,240,191,
+ 86, 5,184, 39, 38, 38,102,195,156, 57,115,186,117,137, 97,118,118, 54, 78,157, 58,133,200,200, 72, 24, 12, 6, 42, 73,210,180,
+148,148,148, 20, 15,188, 0,133,191,194,255,154,162, 64,136,142,142,182, 47, 92,184,176,219, 30, 96,211,166, 77, 48, 24, 12,120,
+244,209, 71,193,113, 28, 14, 30, 60,200,101,102,102, 30, 72, 76, 76, 76, 72, 77, 77,237,246,120,165,194, 95,225,223, 85,116,251,
+ 64,152, 36, 73, 88,191,126, 61, 22, 44, 88,128,190,125,251,194,223,223, 31,137,137,137,136,139,139,227, 84, 42, 85,186, 94,175,
+159,232,203, 54,161,194,255,250,226,223,237, 10, 96, 48, 24, 16, 28, 28,140,136,136, 8, 8,130, 0,173, 86, 11,173, 86, 11,189,
+ 94,143,145, 35, 71,114,106,181, 58, 67,175,215,199,249,234, 11, 80,248, 95, 95,252,187, 93, 1, 10, 11, 11,161,211,233, 26,143,
+ 53, 26, 77,227, 67, 36, 38, 38, 98,248,240,225,188, 90,173, 62,145,144,144,112,131, 47,190, 0,133,255,245,197,191,219, 21, 32,
+ 48, 48, 16, 86,171,115,118, 19,127,127,255,198, 79, 82, 82, 18, 98, 99, 99, 5, 63, 63,191, 44,189, 94, 31,235,107, 47, 64,225,
+127,125,241,239,118, 5,208,233,116, 48,153, 90,167,196,105,208, 98,173, 86,139,164,164, 36, 12, 28, 56, 80,165,209,104,206,234,
+245,250, 1,190,244, 2, 20,254,215, 23,255,110,223, 32, 35, 42, 42, 10, 53, 53, 53,176, 90,173,208,106,235,242,255, 84, 85, 85,
+161,180,180, 20,229,229,229, 40, 45, 45,133,197, 98,193,224,193,131, 33,138,162,250,234,213,171,231,245,122,253,144,180,180,180,
+ 98, 95,120, 1, 10,255,235,139,127,183, 43,128, 90,173,198,248,241,227,145,147,147, 3,157, 78,135, 3, 7, 14,160,160,160, 0,
+177,177,177,136,138,138,194,208,161, 67,193,243, 60, 82, 83, 83, 97, 52, 26, 33,138,162,159, 70,163,201,211,235,245,131,210,210,
+210,188,158,237, 77,225,127,125,241,247,200, 22, 73,211,166, 77,195,167,159,126, 10, 81, 20,241,248,227,143, 99,230,204,153, 80,
+171,213, 78,101, 22, 45, 90, 4,147,201,132,117,235,214, 97,203,150, 45, 90, 74,233,155, 0,158,128, 15, 76, 75, 80,248, 95, 63,
+252, 61,178, 32, 38, 33, 33, 1,129,129,129,248,232,163,143, 48,123,246,108,183,171,168, 66, 66, 66,240,228,147, 79, 66,163,209,
+ 48,171,213, 58, 54, 52, 52,180, 63,124, 32,177, 84, 75,254, 45, 43, 95,225,255,191,195,223, 35, 10, 16, 20, 20,132, 53,107,214,
+ 32, 38, 38, 6,207, 62,251, 44,102,204,152, 1,135,195,225,182,252,144, 33, 67, 36,171,213,106,230,121,254,126, 95,120, 1,205,
+249,119, 4,189,141,191,217, 46,225, 82,105, 45,142, 95,174,192,190, 51,197,136,136,155, 70, 73,212, 40,191,136,184,169,207,196,
+175,248, 79,191,235,169,254, 61,182, 75,164, 32, 8,248,252,243,207,177,122,245,106, 0, 64,114,114, 50, 22, 44,112,189,251,145,
+159,159, 31,163,148, 74,140, 49, 13,124, 36,181,160,187, 94,171, 55,243, 63,122,169, 2,155, 50, 12,200, 41, 50,129,202, 82, 99,
+ 90,119, 22, 54,158, 15,157, 50,118,124, 8,165,227, 41,149,151, 37,190,240,245, 22,202,196,215,210,255,184,232,244,255,122,253,
+ 11,158,124,136, 63,252,225, 15, 0,128,216,216, 88,124,241,197, 23,110, 21,160, 25,122,251,146, 66,159,229,127,185,204,140, 55,
+191,205,134,192, 1, 49, 33, 26, 20,148,137, 96,148,130,177, 86, 31, 2, 70,231,129,146, 95, 76,126,118,253,188,140,119, 23, 37,
+119,250,189,111,248, 9, 89, 5,158,245,167,191,121,246, 94,168,120,238,154,235,223, 99, 10, 80, 84, 84,132,146,146, 18,188,249,
+230,155,120,238,185,231,176,120,241,226, 54,203,247,246,172, 10,190,206,255, 68,126, 37, 24,163,120,235,254, 9, 24, 17, 29,140,
+ 63,109, 59,141,189, 89, 69, 96, 13,189, 64,227, 95,214,112, 76, 64,233, 59, 0, 58,173, 0,207,220, 61, 25, 14,201,179, 85,209,
+ 82,248,187, 90,255, 30, 83,128,236,236,108, 68, 68, 68,224,217,103,159, 5, 33, 4,185,185,185, 46,115,234, 52,215,222,250,165,
+136,189,117,113,138, 79,243, 63, 83,104, 2,165, 20, 2, 87,103, 33,168, 56, 82,215, 3,180,248,180, 80,130, 27,110, 90,178,198,
+255,216, 63,150, 90, 58,243, 91, 57,133,229, 40,175,181, 94, 51,103,209, 97,119,235, 59,206, 26, 59, 24, 92,253, 18, 4,187,221,
+ 14, 89,150, 57, 89,150,213, 0, 66,208,118,126,214,234,230,215, 59,164, 0,159,237,205,196,165,146,206,109,120,146,157,150,138,
+232, 81,147,240,202,198, 84, 72, 14, 59,206,156,191,136, 87,190, 78, 1,199,183,222, 56,239, 80, 77, 8, 95, 54,112,234, 72,235,
+ 0,149, 86, 8, 31, 20, 13,144,118,133, 72, 82,227,143,248,114,101,165, 15,245, 0,180,190, 98,125, 50, 63,168, 67,148,193, 40,
+195,138, 47,143,162, 95,152, 22, 57,133,149,117, 2,207, 24, 24,163,160,204,165, 57, 4,217, 95,173, 6,208, 41, 5,200, 51, 86,
+ 33,191,172,250,154, 57,239, 92,247, 49,210,183,111,236, 72, 81, 53,128, 59,235, 63,111,183, 83,246, 70, 0,103, 58,165, 0,250,
+ 17,253,220,238,249,229, 14, 17, 86, 3,138,250,248,225,238, 73,195,240,233, 71,239, 33,208,223, 31, 63,143, 31,225,186,194, 82,
+183,211, 98, 83,126,161,228, 96,167,164,240,129,223, 18,158,111, 63,197, 96,165,214,210, 93,194, 65,171, 12,224, 66, 59, 54,162,
+110, 50,153, 96,179,217, 16, 21, 21,213,252, 52, 67, 83, 94, 32, 31,237,193,234, 4,221,108,151,113,174,200,214, 36,244,148,130,
+ 82,230,214, 20, 2,215,249, 64,225,162, 91,110,236, 22,198,166, 67,201, 72,175,139,242, 32, 34,194,181,252,157, 57,115, 6,181,
+181,181, 13,141, 80, 25, 99, 44,215,205,237, 70, 1,173,246,153,232,152, 2,140,236,167,235,188, 61, 80, 58, 4, 63, 92,202, 65,
+148,202,129, 13,159,125,130, 25, 51,102, 96,242,176,104,151,101,163, 84, 14,234, 95,109, 40,179,150,151, 95,172,201,220,123, 8,
+ 61,156, 98,220,113, 98, 61,184,136, 17, 80,199,253,162,221,178, 85, 85, 85,152, 59,119, 46,118,239,222,221,242,165, 80, 95,115,
+130, 25, 99, 16,229, 58,125, 92,126,199, 72,136,242, 8,103,253,100,117,255, 63,248,167,173,204, 14,129,184, 50,133, 0,128, 93,
+125,186, 97,177,139, 68,162,255, 42,181,247,187,203,255,189, 27, 39, 47,151, 92,187,227,158, 86,183, 59, 46, 55,106, 6,248,113,
+ 83,157,174,237,122,105, 1,212, 2,143,105,211,166, 33, 61, 61, 29, 0,160,209,104,126,176,217,108, 15,187,145,159, 61, 0,102,
+244,152, 15, 48, 96,192, 0, 28, 59,118, 12,219,183,111,135,205,102,195,252,249,243,219,109,136,235,109,104,175,180,142,246,148,
+ 15, 64, 56, 30,170,209, 63,111,183,244,217,179,103,113,199, 29,119, 96,231,206,157,232,211,167,143, 15,240,119,150,233,140,188,
+ 10,164,158, 47, 65, 70, 94, 57,204, 86, 7, 40,149, 91,181,240, 78,231,160, 34, 13, 38, 80, 75, 83,232,181,159, 93,137, 4,112,
+174,241, 25,175,254,238, 44,152,188,140,196,172,118,155,175,245,131, 71,110,235,150,103,121,222,122, 18,239,103,236,192,138,123,
+226,241,240,195,191,236,136,194,119,186,225,236,144, 2, 56, 36, 25,148,117,174,103, 55,219,108,216,187,119, 47,100, 89, 70,100,
+100, 36,102,205,254, 25,108,162,228, 38,118, 72, 64,121, 1,208,104, 57,220,189,212, 15,186,232,246, 31,100,237, 43,246,142,248,
+ 10,157, 81, 2,219, 79,127, 5, 8, 15,213,168,187,218, 45,157,149,149,133, 59,239,188, 19, 59,119, 54,238,236,234, 19, 81,160,
+ 79,246,229,226,199,204,162, 38, 97,111, 33,216, 77, 2,206,156,237,125, 23,166, 80,235, 42,162, 28,152,116, 35,152,252, 29, 51,
+ 44, 25, 72, 6,252,163,194, 21,135,175,211,114, 96,232, 6, 31,224,104,110,221,252,182, 31, 79, 94, 66,217,119,206, 43, 33,127,
+119,215,205,224,185, 86,238,150,103, 20,224,181, 77,169,157,138,235, 58,204,213, 72, 91,243, 18, 26, 50, 5, 14,152,181, 24,143,
+253, 99,143,251, 22,181, 50, 92, 85, 26, 59,123,170, 72, 84,163, 4, 77,240, 47, 96,110,223,142,150, 22,190,189, 24, 27, 96,236,
+238,158,192,118,224,207, 0,199, 67, 53, 98,118,187,165, 51, 51, 51, 49,123,246,108, 76,154, 52, 9,245,137,182,188,170, 0, 57,
+ 87,107,240,227,233,171,237, 10,182,187,191,172,222,236,113, 45,252, 18,192,228,186, 15,149, 2,192,228,223, 0,120,195,165, 73,
+ 27,226,223, 24,161,185, 22,204,152, 53, 27, 67, 6, 13, 68,220,164,201,232, 31, 17,210, 34,232,224,218,138,104,227,118, 31, 3,
+216, 6,160,184,211, 10,240,214,194, 91, 58, 69,124,225,194,133,176, 86,214,217,128, 43, 86,172,192, 27,111,188,209,102,249,167,
+159,126,218,177,235,232,174, 93,165,165,165,187, 42, 42, 42,190,132, 87,183, 25, 98,176,237,255, 35, 8,199, 67, 24, 62,171,221,
+210, 39, 78,156, 64, 97, 97,161, 42, 40, 40,136,247,182, 15,176,247,140,177, 93,193,102, 45,206, 57,149,173,239, 33,154,161,118,
+214,232,138, 64, 48, 9,160,178,179, 18, 48,233,255,220, 41,192,164,161,125, 33,201,215,254, 10,111, 31, 59, 8,192,189, 46,175,
+185, 81,176,182, 26,206, 45, 93,238, 1, 58,131, 77,155, 54, 97,243,230,205, 0,128,233,211,167, 99,220,184,113, 29, 14, 35,250,
+130, 13, 93,223,213,195,186,247,109,104, 9, 15, 97,216,204,118,139,151,148,148,112, 85, 85, 85, 51,181, 90,237, 78,111,210, 46,
+ 40, 51,183, 22,108, 39,211,135,181,109, 10, 81,218,232, 24,215,139,211, 14, 63, 34,198,131,214, 11,190,179, 18,244,101,185,247,
+ 69, 76, 93, 92,236,210, 98,200,204,247,236, 72,240,182, 23,230, 65, 45,240, 61,227, 3,116, 20, 70,163, 17,203,150, 45, 3, 0,
+ 60,245,212, 83, 88,190,124, 57,222,127,255,125,220,119,223,125,237, 9,191,207,216,208, 78, 74,176,231, 13,104, 57, 30, 66,236,
+244,246,205, 62,135, 35, 66,146,164, 21, 0, 54,163,110,176,165,199, 81,108,178,180, 22,236, 86,145,157, 54, 76, 32,103, 63,239,
+220,188,201,149,175,129,138, 59,235, 91,252,230, 38, 80,195,255,195, 93,241,248,243,131,183,122,235,173,121, 70, 1, 58, 58, 16,
+182,229,253,151, 80, 94, 94,142,126,195,227,224, 55,241,110,124,188,247, 44, 54,126,247, 3, 28, 3, 39, 35,172,175,251, 73,134,
+233, 53,193, 66,241,128, 91, 38, 89, 7,106,116, 66,112,244, 77, 62, 51, 16,198, 40,172,187, 95,131,246,118, 30,194,144,169,237,
+215, 62,165, 35,234,237,204,159, 1, 48,247,228,155,183,139, 50,202,170,173,109, 10, 56, 24,197,168,126, 97, 24, 30, 19, 10,127,
+ 53, 95,175, 36, 12,187,247,236,145, 10,140,101,217, 18,175,189,164, 14, 31,144, 77,128,172,111,127,115,246,252,128, 80,219, 23,
+ 96, 82,180,139,214, 31,245,102,209, 48, 87,202,254,238,119, 25, 56, 95, 84,225,209,231,253,248,241, 89,174,230, 2,121, 70, 1,
+166,223, 56, 16,147,134, 58,218,142,138,156, 58,129, 11,199,211,160,235, 19,129,127,253,123, 45, 34,162,250,226,245,149,207,162,
+164, 32, 23,255,120,254, 33, 68,247,235,143, 71,150, 62,137, 95, 44, 92,212,186,235, 78,219, 78, 75,170, 46, 94,144,236, 72,167,
+129,186,253,224, 85,237, 63,136, 40,246,140,128, 81, 25,214, 93,175, 64,123,199, 27, 16, 6, 37,118,228, 27,183,212, 43,193, 28,
+ 0,214,158, 82, 0,158, 35, 0, 99,110,109,252,176, 64, 53,126, 63,111, 18,110, 30, 80, 14, 34, 93, 6, 88,211,134,246, 55,251,
+149, 18,201, 94,174,234, 19, 74,252, 71, 13,171,138, 38,160,119,130, 74,227, 65,101,190,141,214, 31, 96, 82,128, 43, 5, 88,144,
+ 56, 10, 86,187,103,115, 4, 11,174, 7,232,152, 71, 20, 32, 54, 42,180,221, 50, 23,143,213,201,227,250,117, 95, 96,230,228,177,
+ 88,191,126, 61,190,251,230,171,198,235, 87, 11,175,224,237,151, 95,192,200,193, 49,120,224,129, 7,156,190,219, 71, 37,202, 1,
+181, 87, 75,106,141,198,139,181,153,123, 79,194,215,246,218,165, 18,172, 59, 95,134,118,214,155, 0, 58, 52, 71,253, 86, 0,223,
+ 1,184, 27,128,173, 39, 40, 10, 60,135,240, 0, 21, 74, 76, 98, 43, 27,159,128,225,181, 7,166, 96, 92,216, 15,224,106,178, 90,
+125, 87, 63, 30, 60, 88,232,104, 80,121,180,139, 86, 30,173,148,160, 73, 17,114, 80, 55,247,198, 9,102,155, 3,213, 86,199,255,
+142, 9,212, 17,148,151,151, 35, 52, 52, 20, 51,103,214, 57,141,111,189,245, 22,198,141, 27,135,249,243,231, 35, 47, 47, 15, 35,
+ 71,142,196, 59,239,188,131, 23, 95,124,177,149, 2, 52,115, 96,124,119, 54,168, 44,194,150,242, 30,144,240,118, 71,191,113, 27,
+128,135, 0,252,163,167, 40,246, 13,209,194, 88, 89,219,202,244,153,114, 67, 20,198, 70, 21,128,171,205,114,209,102,182, 16,112,
+ 87,166,142,203,243, 50, 64,165,179, 0,166,180,188,229,206, 83,151,112,161,216,179,214,233,196, 33, 81, 16,122,202, 4,170,181,
+ 57,218, 13,107,197, 12, 28,140, 81,163,111, 68,149,217,134,146, 18, 35,114,115,115,241,205,214,239, 16, 63, 37, 1,143, 62,180,
+ 8,171,222,125, 15, 34, 5,126,191,226, 57,100,229, 92, 64,255, 1, 77,115,111,236,148, 16, 89,229,175,146, 2,250,248,225,230,
+135, 67,161, 13,110,255, 65,198,163, 26,175,190,218, 99, 61, 5,231,175,131,118,206,187, 40, 55,117,184,151,125,191, 39,133, 31,
+ 0,134, 68, 4,226,100, 94, 73,171,112,231,232, 1,225, 32,226,233,214,214, 66, 91,173, 60,117,161, 4,206,231,175,144,184,148,
+226,164,164,164, 86, 60,150,253,108,146,119,226, 22,158,138, 2,253,101,219, 17,100, 27,218, 14,107,201, 14, 59, 78, 95,184,132,
+ 37,107,118,128,202, 18,180, 33, 58,124,145, 85,131,245, 57,251,144,117,165, 2, 75,214,236,128,100,139, 0, 39,168,240,252,231,
+ 59, 17, 24,209,228, 20,103, 85,135,169,138, 7,207,184,205, 65,212, 99, 4, 77,224, 67, 29,114,130, 79, 9, 75, 0,148,244,152,
+240,207,253, 0, 92,232, 64,192,148,223, 81,225,255, 93, 79, 11,192,188,248,193,248,238, 72, 30,100,217, 57,220, 25,232,167, 2,
+161,181, 78,206,125,199, 90,249,230,202,209,226, 26,240, 23,119, 60,126,253,207,157, 56,158,231,217, 44, 43, 7,223,248, 85,171,
+ 48,168,199,122,128, 87,238,239,144,243,135,249,199, 55,227, 47,247,223,132, 1, 3, 6,224, 29,249, 34,180,154, 34, 44, 95,190,
+ 28,203,243,247,225,165,135,146,224,231,231,135, 81,127, 95,129,109,111, 62, 1,190,217,180,232,103,158, 57,232,216,115,108, 79,
+178,209,104,252,161,188,188,124,191, 47,249, 0, 78,194,223, 49,124,224, 13,225, 7,128,200, 16, 45,102,143, 31,128,173,135,115,
+157, 28, 96,231, 9,112,157,106,229, 91, 40,135,220,240,106, 74,219,234,221,254,254,248, 44,175,188,171,102,251,187,245,188, 15,
+ 0, 0,127,255,251,223,241,252,243,207,227,239,127,255, 59, 94,120,225, 5, 36, 39, 39, 67,146, 36,140, 27, 55, 14,199,143, 31,
+ 71,126,126, 62,238,184,227, 14, 39,225,111,230,189,203,148, 82,159,154, 78,220, 89,225,231,121,254, 27, 89,150,127,231, 77,206,
+191,190, 35, 14,126, 42, 14, 7, 78, 27, 80, 92, 89, 11, 6, 82, 63,106, 74, 1, 38,186,108,229,101, 81, 6,152, 36, 19, 34, 83,
+ 14, 50,117,171, 4,117, 14,253, 81, 0,207,146,184, 84,183,211,209,119,158,186,132, 18,147,197,163,207,185, 48,105,116,171,185,
+ 64,245, 38, 16,243,154, 2,232,116, 58,188,248,226,139, 88,185,114, 37,238,186,235, 46,220,123,111,221, 48,246,152, 49, 99,240,
+250,235,175,227,198, 27,111,196,154, 53,107,220,105, 47,245,165,129,176,206, 10,127, 80, 80,208, 17,149, 74,245, 65, 69, 69,133,
+ 87,121,171, 4, 14, 75,102,197, 97,201,172, 22, 9,148, 77,123, 1, 42,186, 52,117,254,181, 45,216,158,113,228,196,231,209, 97,
+214,159, 94,249, 77,255,227, 42,158,177,102,189,193,121, 18,119,176, 83, 61,178, 40, 83,183, 19, 31,123,101, 20,232,147,157, 39,
+144,107,172,234, 56,139,209,183,227,131,173, 7,241,202,223,214,163,232, 66, 54,170,203,141,144, 28,118,140,184,255,183,120,225,
+203,159, 90,219,115,213, 33,234, 43, 3,111,157,105, 25,172, 29, 42,248,135,221,215,145, 69, 85, 18, 52,175, 99,211,211, 21,190,
+ 32,252,227,198,141,147, 36, 73,218, 89, 88, 88,232, 91,225,219, 22,161,220,186, 86,189,181,169,179,244,238, 18,205,210,187,162,
+150,128,201, 75, 90,181,254, 96, 97, 0,170, 58,243, 83,115, 38, 14,245,150, 19,236, 25, 19,104,214,184, 33,168,181,117, 50,174,
+123,155,243, 62, 6, 75, 23,221,143,135,166,141,113, 89,180,228,200,143, 82, 85,213,197,147,146,168, 74,113, 12,158,156, 5,194,
+117,224, 65,170,107,125, 65,248,151, 45, 91, 6,198,152, 99,223,190,125, 62,190,168, 95,114,107, 2, 57, 69,129, 84,209,102, 16,
+129,192,122,222,191,203,102, 88, 39,157,224,221, 47, 63,128, 32,173,218,119,123,128,142, 12,132,181,135, 49,163, 70, 96,236,160,
+ 72,151,215,250,168, 68, 57,168,182,176,168,186,176,240,172,249,232,182,147,222,242, 3,186, 34,252,239,190,251, 46,158,121,230,
+ 25,230,107, 38, 92,235,214,145, 7,105, 48,129,220,216,248,148,105,109, 92,236,218, 0, 16, 14,184,176,160, 22,142, 66,127, 0,
+246, 78,251,130, 94,114,130,225,205,129,176,230, 56,113,226, 4,190,252,242, 75, 76,157, 58, 21,115,231,206, 5, 0, 12, 29, 58,
+ 20,178, 44,187,114,128, 27, 39,195,213, 59,193,232, 77,194,239, 43,252,219, 85, 0,213, 96,192,156,222,102,180,135, 48,137,135,
+ 92, 13,112, 26, 64,174, 38, 0, 78,146,184, 84,171,175, 61,203,246,237,219, 81, 88, 88, 8, 0, 40, 46,110,234,105, 40,165, 19,
+209,148, 31,116, 63,128,156, 30, 87, 0, 74, 41,230,205,155,135, 43, 87,174,224,227,143, 63,198,241,227,199, 49,114,228, 72,132,
+132,132,192,106,181, 34, 48, 48,208,149,237,230, 85, 39,152,248,247,233,178,240,251, 2,255, 14,189,151,192, 89,224, 44,135, 64,
+172,103, 93,155, 64,160, 32,128, 10,231,127,110, 7, 56, 6, 38,137, 0,150,250,226,179,172, 94,189, 26,251,246,237,115, 37,123,
+115, 80, 55, 7, 11, 0, 30,243,138, 2,212,214,214,226,202,149, 43,141,202,208,208,226, 23, 23, 23, 67, 20, 69,119, 17, 32, 48,
+198,168,220,176,132,172,135,161,185,249, 49,128,227, 59, 84,182, 95,191,126, 78,194,239, 11,252, 59,166,229, 42, 72, 81,175,131,
+ 51,167,129,171, 88, 7, 98,191,220,220,209,109,214, 26,201,118, 64,126, 15,192,123, 36, 46,213,228,139,143,242,231, 63,255, 25,
+149,149, 77, 83, 45,254,246,183,191,217, 14, 31, 62,188,174,180,180, 52, 77, 20,197,252,250, 7,202,233,200,189,186, 93, 1,130,
+131,131,113,251,237,183, 35, 59, 59, 27,159,127,254, 57,134, 15, 31,142,140,140, 12, 24,141, 70,132,133,133,185,127, 63,222,204,
+172,214, 65,225, 7,220,231,172,236, 29,153,237, 8,104, 64, 34,104, 64, 34, 32, 87,129, 56, 10, 64, 28, 6,108,217,188,209,158,
+151,119,225,115,115,109,229, 87, 99,134, 9, 63,205,127,250,156, 79, 63,199,216,177, 99,157,142,183,109,219, 38,231,230,230, 94,
+ 48,155,205,135, 76, 38,211,185,206,248,144, 30,241, 1, 54,110,220,136,215, 94,123, 13,159,125,246, 25,190,255,254,123,232,116,
+ 58,124,240,193, 7,237,125,173, 87,167, 70,236,117,252,249, 80, 48,109, 40,152,118, 44, 82,206,236,147,246,239,207, 62, 87, 80,
+ 80,126,165,170,170,138, 94, 79,245, 47, 0,128,201,100, 18, 50, 50,186,119,255,228,150,171,192, 78,158, 60,233,182,172,201,100,
+226, 9, 33, 93, 54, 33, 60,193,191,147,191,175,240,239,165,252, 5, 0,198,226,226,226, 83,171, 86,173,226,237,118,123, 52, 99,
+ 76, 13,128,213, 71, 54, 88,179, 15,234,207, 55,254,223,242,154,187,235, 45,238,213,178, 44,147,101, 89,150, 36,169,164, 62,189,
+ 96,103, 67,160, 10,127,133,127,151,249, 55, 31,114,229,116, 58,221,114, 0,125,209,148,229, 76,102,140, 73,132, 16,153, 49, 38,
+ 19, 66,164,102,231,104,179,107, 13,231,101, 66,136, 84,191,184, 93,110,184, 70, 8,145, 41,165, 82,139, 99,185,193,110,166,148,
+ 74,178, 44, 75,140, 49,139,217,108,190,210, 85, 75, 94,225,175,240,239, 44,255,230, 10, 64, 2, 3, 3,163, 57,142, 83, 19, 66,
+152, 74,165,130, 40,138,141, 90,214,160,133,205,143,235, 67,127, 12, 0, 28, 14,135,147, 6, 19, 66, 88,179, 79, 67, 89, 88, 44,
+ 22,167,123,112, 28,199, 8, 33,172,178,178,146,213, 87, 90, 87,215,210, 41,252, 21,254,157,230, 79,218, 57,238, 40,124,101, 6,
+167,194, 95,225,223, 35,132,187, 5, 73, 73, 73, 2,128,217, 28,199,221,247,211, 79, 63, 45,238,109, 97, 7,133, 63,144,148,148,
+ 52, 90, 16,132, 71, 8, 33,221, 46, 75,140,177,112, 89,150,135, 51,198, 94, 78, 73, 73,217,231,137, 58, 16,186,169, 34,251, 1,
+ 40, 79, 73, 73,177,117,176,252,120,181, 90,189,132, 49,246, 43,157, 78,199,149,149,149, 9, 0, 22,123, 81, 16, 20,254, 93,231,
+127, 67,100,100,228,147,115,230,204,241,235,206,103,202,206,206,198,169, 83,167, 16, 25, 25, 9,131,193,176, 59, 41, 41,105, 90,
+ 74, 74, 74,138,207, 40, 64, 82, 82, 82, 8,128,121, 90,173,246,215, 14,135, 99,188, 32, 8, 59,146,146,146,230,166,164,164, 48,
+ 55,229, 35, 57,142,123, 80,173, 86,255,159, 32, 8, 81,241,241,241,154, 73,147, 38, 9, 90,173, 22,111,190,249,166,205, 11, 66,
+163,240,239, 38,254,209,209,209,246,133, 11, 23,118,155, 2,108,218,180, 9, 6,131, 1,143, 62,250, 40, 56,142,195,193,131, 7,
+185,204,204,204, 3,137,137,137, 9,169,169,169, 25, 94, 83,128,164,164, 36, 53,128,217,126,126,126, 75,101, 89,158, 62,108,216,
+ 48, 41, 62, 62, 62,104,232,208,161, 88,179,102,205,173, 37, 37, 37,239, 2,120,166, 69,249,185, 90,173,246, 73, 73,146,226,227,
+226,226,104,124,124,188,255,224,193,131, 27, 38,144,193,106,181,246,164,208, 40,252,189,200,191, 35,144, 36, 9,235,215,175,199,
+210,165, 75, 17, 22, 22,134,218,218, 90, 36, 38, 38,130, 82,202,101,101,101,165,235,245,250,155,211,210,210,142,247,152, 2, 36,
+ 37, 37, 17, 0, 73, 26,141,230, 49, 74,233,188,190,125,251,202, 83,166, 76, 9,137,139,139,131,159, 95,147,210, 63,246,216, 99,
+ 1,239,189,247,222, 19,183,220,114, 75, 14,165,244,148, 70,163, 89, 74, 41,157, 31, 19, 19, 67, 19, 18, 18,130,227,226,226,160,
+ 82,169,188, 97, 30, 40,252,189,200,191,179, 48, 24, 12, 8, 14, 14,110,220,124, 68,171,213, 66,150,101,232,245,122, 72,146,196,
+229,228,228,100,232,245,250,241,105,105,105, 89, 30, 85,128,122,231,102, 49,199,113,143, 6, 6, 6,170,227,227,227, 3, 38, 76,
+152,192,135,132,132,184, 44,239,239,239,143, 37, 75,150,248,175, 94,189,250, 35,173, 86,235,152, 50,101,138,118,226,196,137,124,
+104,104,104,183, 85,206,244,233,211,251,216,237,118,154,158,158, 94,209, 1,193, 81,248,123,145,127, 87, 81, 88, 88, 8,157,174,
+105, 71, 34,141, 70, 3, 89,150, 33,203, 50, 18, 19, 19, 33,203, 50,127,225,194,133, 19, 9, 9, 9, 55,166,167,167,159,239, 86,
+ 5, 72, 74, 74,138,225, 56,238, 87,106,181,122, 9,199,113, 49,147, 38, 77, 18,110,186,233, 38,117,223,190,125, 59,116,179,136,
+136, 8,172, 92,185, 82,237,239,239,175,238,206, 74, 73, 76, 76, 28, 17, 16, 16,176,210,110,183,223, 86, 93, 93, 29,219,134,208,
+ 40,252,189,200,191, 59, 16, 24, 24,216,202, 44,243,247,247,111,220,212, 59, 41, 41, 9,178, 44, 11,151, 46, 93,202,210,235,245,
+ 35,211,210,210,242,186, 69, 1,146,146,146, 18, 4, 65,216, 59,102,204, 24,122,243,205, 55,251,199,198,198,162, 43,145, 45,127,
+127,255,110,171,140,169, 83,167, 78, 11, 8, 8,120,153, 82,154, 16, 16, 16,160,150,101,249,163,236,236,108,135, 27,225, 81,248,
+123,145,127,119, 65,167,211,193,100,106, 61, 11,187,193, 20,146,101,185, 65, 9, 84, 5, 5, 5,103,245,122,253,176,180,180, 52,
+195, 53, 43,128,159,159,223,107,208,238,250,153, 0, 0, 20,252, 73, 68, 65, 84,119,222,121,167, 58, 33, 33,129,131, 23, 49,125,
+250,116, 65,150,229,251,252,253,253, 95,241,247,247,239,255,224,131, 15, 6, 76,159, 62,157, 44, 88,176,192,102,177, 88, 62,114,
+247, 61,133,191,119,249,119, 23,162,162,162, 80, 83, 83, 3,171,213, 10,173, 86, 11,160,110, 99,194,210,210, 82,148,151,151,163,
+180,180, 20, 22,139, 5,131, 7, 15,134, 40,138,234,171, 87,175,158,215,235,245, 67,210,210,210,138,187,172, 0, 73, 73, 73, 35,
+ 1, 36, 77,154, 52,201,107,149, 31, 31, 31, 31,172,209,104,150, 8,130,176, 98,232,208,161,154,135, 30,122, 40,104,202,148, 41,
+ 32,132, 96,247,238,221, 16, 4,225, 84,122,122,250, 69, 55,173,167,194,223,139,252,187, 19,106,181, 26,227,199,143, 71, 78, 78,
+ 14,116, 58, 29, 14, 28, 56,128,130,130, 2,196,198,198, 34, 42, 42, 10, 67,135, 14, 5,207,243, 72, 77, 77,133,209,104,132, 40,
+138,126, 26,141, 38, 79,175,215, 15, 74, 75, 75, 43,237,146, 2,104, 52,154,151,166, 78,157,170,242, 70,148,160,186,186, 26, 28,
+199,169, 2, 3, 3,139, 38, 79,158,140, 95,253,234, 87, 1, 55,220,112,131, 83,153,111,190,249,166,166,182,182,246,207,238,238,
+161,240,119,195,205, 38,225,167,139,165, 40,169,113, 64, 45,112, 80,243, 4,106,158,131, 70,224, 48, 97, 64, 40,250, 6,251,117,
+ 11,255,238,198,180,105,211,240,233,167,159, 66, 20, 69, 60,254,248,227,152, 57,115, 38,212,106,103,183,102,209,162, 69, 48,153,
+ 76, 88,183,110, 29,182,108,217,162,165,148,190,137,166,245,192, 29, 87,128,164,164,164,104, 74,233,189,122,189, 94,232, 73,193,
+ 41, 44, 44, 68, 74, 74, 10,206,157, 59,135, 57,115,230,240, 11, 22, 44, 8,136,140,108,157, 53, 34, 63, 63, 31, 5, 5, 5,148,
+231,249,111,221,180,158, 94,231, 63,243,206,159,241,139,127,249,128, 79,240,183, 75, 20,169,121,229,216,157, 83,130,140,252, 74,
+136,110,146, 26, 19, 0, 3, 53,118,220,104,207,198, 67,119, 37,240,183,205,127, 34, 32, 50, 50,170,211,252, 61,129,132,132, 4,
+124,253,245,215,120,227,141, 55, 16, 19,227, 62, 29,125, 72, 72, 8,158,124,242, 73,108,223,190,157,213,212,212,140, 13, 13, 13,
+237, 95, 85, 85,117,165, 51, 74, 32,168,213,234,231,110,186,233, 38,174, 59,157, 39,119, 96,140, 33, 39, 39, 7,169,169,169,168,
+172,172,196,125,247,221,135,215, 95,127,189, 77,199, 45, 57, 57,217,193, 24, 91,179,127,255,126,201, 77,151,233, 85,254,137,243,
+ 30,197,211,235,126,194, 61,178, 10,145, 94,228,207, 24,240,245,113, 3,214, 30, 42,128, 85,108,127, 93, 8, 3,144,111,215,224,
+151,131,181,184, 91,216, 3,203,119,199, 96, 31, 57, 3,252,144,169, 16,162,199, 55, 46, 19,109,143,191, 39, 16, 20, 20,132, 53,
+107,214,184, 93,126,218, 18, 67,134, 12,145, 12, 6,131,153,231,249,251, 81,151,152,184,227, 10,192,243,252,207, 39, 77,154,164,
+241,228, 3, 73,146,132, 99,199,142, 33, 45, 45, 13, 1, 1, 1, 88,184,112, 33,166, 77,155,230, 50, 69,138, 83,107,102,183, 99,
+231,206,157,212,106,181,254,205, 93, 25,111,242,207,200, 45,198, 93,171,190,129,213, 33,225,238,119,190,193,190, 87, 23, 34, 58,
+ 44,176,199,249,151,155, 29,120,251,199,115, 56, 90,208,249,156,252, 19, 2,235,190,227, 47, 85,193,145,181, 5,200,218, 2,226,
+ 23, 12, 97,144, 30,108,128, 30,251,246,180,205,223, 83,232,168,240,215, 7, 16, 24,165, 84, 98,140,105,208,201, 9,158, 2, 0,
+194,113,158,241,189,204,102, 51,210,211,211,113,248,240, 97,140, 26, 53, 10, 43, 86,172,232,240,174,145, 0,176,111,223, 62, 8,
+130,112, 36, 45, 45,173,173,156,228, 94,225,159,109, 40,195,188,119,183,194,234,168,107, 24, 11,202,170,113,239,159,147,177,243,
+165,249, 8,214,106,122,140,191,201, 38,225,183,155, 51, 81, 80,209,249,100,180, 4,192,248,160,214, 89, 15,153,173, 26,226,185,
+ 29,192,185, 29,248,247,108,162, 82, 17,246, 23,242,192,148,100,104,196,239,195,151, 30,243,201, 76, 17,245,232,218,154,224,238,
+ 70,105,105, 41, 82, 83, 83,145,153,153,137,105,211,166,225,195, 15, 63,196,128,102, 27, 98,116, 20, 61,237,124,117,148,127, 65,
+ 89, 53,230,190,243, 13,170,204,206,115,200, 50,243, 75,176,240,253,109, 72,126,238, 94,168, 5,222,227,252,173,162,140,231,147,
+ 79,119, 73,248, 1, 32, 86, 91,139, 16,161,237,245, 35, 42,142,241, 0,230, 49, 96, 58,236,170,229,229, 31, 76,249, 74,144,201,
+218,144,167,211,189,155, 5,152, 81,128, 52, 53, 28, 93,205,202,209,173, 10,144,151,151,135,148,148, 20, 20, 22, 22, 98,238,220,
+185,120,238,185,231,208,213,161,248,220,220, 92, 92,189,122, 85,140,142,142,254,111, 79,213,105, 71,248,151,152, 44,152,179,106,
+ 19,174, 86,185,222,163,111, 95, 86, 62,150,124,178, 3, 47,222, 57,210,227,252,255,153,122, 25, 57,198,154,182, 91,121, 2,232,
+ 71,244, 71, 76, 88, 0,204, 54, 17,149,102, 59, 14, 95, 40, 2,101, 12, 19,130, 42,219,234,151,144,122,133,179,199,199,208, 39,
+ 52, 4, 7, 67,151,165,229,250, 66, 19, 79, 45,229,176,253,176, 18,204, 82, 6,245,228, 37, 80,141,184,163,177,245,175, 95, 74,
+217,233,244,232,215,180, 26,135, 82,138,204,204, 76,164,166,166, 66,150,101, 60,240,192, 3,184,253,246,219, 91,133,173, 58,139,
+173, 91,183,218, 41,165, 31,111,218,180,169, 61,173,238, 49,254, 53, 86, 7,238,249,211, 22,228, 22,183,157, 44,121, 99,122, 14,
+ 12,185, 57,178,218,131,252, 47,150,214, 34,249, 84,161,219,235,129,126,106,172,184, 39, 30, 11, 18, 71,161,127,120,144,211,181,
+203, 37, 38,124,180,227, 56, 6, 95,106, 61,159,204, 6, 13,252, 96, 7, 24,197,153, 50, 97,227,220, 63,166,172,245, 37, 27,135,
+ 85, 23, 65,174,200,173,219,179,109,223,219, 16,179,147, 17,227, 7, 82,191, 32,158,118,197, 7,232, 18, 28, 14, 7, 14, 29, 58,
+132,244,244,116,244,239,223, 31, 79, 60,241, 4,226,227,227,209, 29, 11,131,108, 54, 27,246,236,217,195,108, 54,219, 39,158,170,
+200,206,242,183,139, 50, 22,188,247, 45, 78, 94, 54,118,232,254,233, 37,224, 53, 33,137, 20,216,227, 17,254,255, 72,201, 3,117,
+163, 58,209, 97,129,216,242,236,189, 24, 55,216,117, 50,226,193,145, 33,120,247,161, 91, 81,242,229, 23, 78,155,156,214,112, 65,
+ 8,162, 77, 61,202,226, 56,199,224, 23,124,204,200,231,251,142,129,118,214, 27,176,238,124, 9,144, 69,200, 37,103,241,255, 6,
+ 16,149,223, 20,255,193,111,109, 39, 93,234, 1,186,132,109,219,182,129, 82,138, 85,171, 86, 97,248,240,225,221,250,144,123,246,
+236,129, 32, 8,169,169,169,169, 69,158,170,200,206,240,167,140,225,145,143,183, 99,127,118, 65,167,126,195,206,107, 95,230,231,
+175, 58, 39,111, 92,185,161, 59,185,151,155, 29,200,200,175,116,217,216, 13,208, 5, 97,247, 43, 11, 49, 64, 23,212,142,187, 40,
+ 66,107,174,123, 30, 17, 2,100,162,114, 18,126, 0, 80,243,152, 90,249,158,126,124,216,239,210, 78,250,146, 18, 8,131,244,208,
+206,122, 3,182,157, 47,131,201, 14,240,132, 97,241, 36,191,113, 83, 6, 14,122, 88, 16,134,173,155,252,234,225,234,142,222,139,
+ 67, 23,246, 21, 48,155,205,200,204,204,196,202,149, 43,187, 93,248, 27,156, 95,179,217,220, 81,231,209,227,252,151,125,182, 27,
+ 91,143, 92,232,202,163, 16,194,176, 86,184,127,213,140,238,228,191, 35,171, 16,204, 77, 79,255,135,121,250,246,133, 31,128, 92,
+ 94,103, 70,128, 87, 33, 48,225, 9,248, 49,215, 11, 99, 40, 47,223,235,139,225, 30, 97,144, 30,126,179,255, 8,162,210, 54,158,
+ 27, 17,169,158, 52, 52,156, 28, 42,251, 48, 97,164, 71,123,128,163, 71,143, 34, 33, 33,161,205, 92,159, 93,197,185,115,231, 80,
+ 82, 82, 98, 59,120,240,224, 78, 79, 85, 94,103,248,191,254, 77, 42, 62,219,155,121, 45, 63,167, 6,144,172, 90,240,206, 45,226,
+215, 47,156,234, 14,254,169,103, 93, 79,126, 28,216, 39, 24, 11,147, 70,119, 44, 94, 88,114, 6, 32, 28,180,183,191, 6, 97,112,
+ 18,196,236,100,208,106, 23, 62, 5, 35, 9, 61,102,223,215,150, 64, 42, 60, 6, 72,118, 48, 89, 4,100, 7, 24, 21, 65,168, 4,
+230,176,130, 57,106,193, 28,181,128,104, 1,179,155,235,254,111,189, 51,234, 40,194,216,225,242, 15, 19,230,235,158, 74,255,177,
+219, 21,128, 82,138,140,140, 12,188,252,242,203, 30,169,132,173, 91,183,218, 68, 81,252, 0, 30, 74,149,209, 25,254,127,251,241,
+ 56,222, 73, 62,212,120, 28,164, 85, 99, 70,220, 32,216, 68, 9, 63,158,188,228,186, 66, 9, 16,224,168, 56,100, 82,133,107, 0,
+ 76,168, 63, 29,204, 40,251,193,239,129, 85,122,219, 87, 43, 47, 95, 43,255,203,149, 86,128,104, 91, 93, 91,116,203,141, 80,241,
+ 29, 27, 83,160, 37,103,161,137, 95, 10, 97,112,221, 62,191,170,225, 51, 97, 63,246,133,139, 62, 12, 61,178,233,175,116, 97, 39,
+172,123,223,118, 37,208, 93, 65, 48, 24,219, 94,241, 97,252,178,240,167, 14,255,173, 61, 19,168, 83, 56,127,254, 60,130,130,130,
+ 16, 23, 23,215,237,149, 96,177, 88,176,127,255,126, 56, 28,142,127,122,170,162, 59,202,255,235,180, 28, 60,183,110, 31,162,195,
+ 2,241,248,109,227,240,237,138,121, 48,124,242,127,216,240,219,185,109,239,129, 69, 37,140, 40, 73,253,185,180,105,229, 68, 9,
+100, 16, 1,158, 2,176, 27, 64,164, 36, 99, 7,238,125, 91,119,173,252, 45,196,245,250,243,168,144,128,142,219,102,234, 0,168,
+199, 63,208, 36, 8, 49, 19,221, 21, 13,233, 9, 5, 16,207,239,236, 46,225,111,244,151, 25, 35, 31,151,127,144,240, 62,123,213,
+189,156, 11,157,221, 91,245,240,225,195,248,197, 47,126,225,145, 74,216,181,107, 23, 83,171,213,123,247,236,217,211,225, 13,176,
+ 61,193,127, 87,230,101,252,117, 91, 6,214, 44,189, 19, 11,244,163, 58,220,170, 2, 0, 3,145,210,210,210,234,248,111,122,161,
+ 64, 4, 62, 2,240,145,102,193,159,134, 74,178,252,172, 32,112,155,164,251,255, 58, 7,155,158,182,118,149,191,138,143,133, 67,
+110,253,181,176, 64,103,197, 56,124,161, 8,195,163,195, 17,222,226, 60, 24,133,122,226,131,206, 78,180,228, 54, 49, 4,199, 54,
+222,207,147,249,155, 60,154,249,218,111,198,139,144, 75,178, 1,209, 10, 38, 90,193, 28, 22,192, 81, 3,106, 53,129,150,157,131,
+ 92,226, 58,221, 63, 31, 58, 16,124,248, 96, 64,208,128, 89, 42, 32, 22,157,172,223,240,163, 65, 64,216,242,242,176, 41, 67, 75,
+ 62,246, 91, 24,249,155,253,181, 93, 54,129, 24, 99, 40, 47, 47, 71, 65, 65, 1,110,187,237, 54,143, 84,194,166, 77,155,204,213,
+213,213,239,122,196,190,236, 32,127,179, 93,132,192, 17, 28,122,251, 33,116, 37,162, 75, 9,231,114, 79, 45,251,215,207,231, 2,
+248, 53, 22,190, 21, 37,136,142, 9, 18,144,214, 85,254, 1,125, 71,194, 97,110,253, 51,205,103,126,214,218, 28,120,107, 75, 58,
+190, 91, 49,207, 69,171,193,129,248, 59,119, 68,204,230, 54,112, 34,226,204, 38,143,103,110, 35,218, 80, 8,131, 90,111,200, 46,
+ 95,205,132, 53,111,127,171,243,170,126, 19,161,141,127, 28, 66,191,241,173,158,195,126,126, 39, 44, 41,171,235,156,124, 0,132,
+224, 46, 94,182,165,148,175,142,191, 75,183,236,240,149, 78, 41, 0, 99,245, 59,142, 51,134,195,135, 15, 99,214,172, 89,208,104,
+186,127,238,217,153, 51,103, 80, 85, 85, 85,147,154,154,186,175,187, 5,191, 51,252, 3, 52, 42,220, 26, 55,168,235,191, 7,210,
+246,172,201, 13,127, 48, 74,128,241, 90,248, 27, 11,131, 81,105,110,189,246, 99,219,145, 11, 88,152, 56, 10,140, 1,203, 63,219,
+141, 62, 65,218, 14,243, 46,185,120, 28,193,174, 47, 93, 32,175,194, 43,123, 6, 72, 23,247,192,186,239,237, 70, 65,110,236, 45,
+110,122, 8,254, 9, 75, 27,167, 66,156, 59,127, 6,102,179, 25,186,112, 29, 6, 13,138,133,223,216,251, 32, 68,220,128,154,237,
+ 43,192,172,141,131,150,227, 0,238, 61, 0,247,119,216, 7,160,148, 54,174,195,180,217,108, 56,126,252, 56,238,185,231, 30,143,
+ 60,236,150, 45, 91,172,162, 40,190,215,221, 14,111, 79,241,247,148,195,238,138,255,228,225,209, 46,203,239,204,188, 12,139, 93,
+196,239, 55, 28,192,134,212,179,152, 60, 44,186, 99, 74,230,176, 64,147,191,219, 77, 43, 79,206,244,248,131, 51, 10,251,225, 53,
+176,238,126,189,149,240,171,135,205,128,191,254,215, 0,225,112, 56, 35, 29,241, 79,188,138,184, 23,191, 67,252,170, 61, 24,246,
+220, 70,252,252,153, 55,112,241, 98, 14,132,232,177, 8,185,255, 95, 32,126,205,167,178,176,123,171, 62,156, 60,164,165, 2,180,
+138, 67, 55,175,248,134, 79,102,102, 38,134, 13, 27,134,254,253,251,119,251,243,214,212,212, 32, 53, 53,149,216,108,182, 79,187,
+214,200,123,151,255,181,119, 82,157,227, 63,101,120, 63,215, 65, 4,187,136,121,127,217,138, 15,182, 31, 5, 0, 76, 30, 22,211,
+ 33, 2,181,199,191,130,134,147,220, 24,124,108,103,143, 42,189,185, 12,150,109,203,225, 56,241,159,214,129, 64, 65, 3,255,233,
+207, 2, 0,242,242,206,227,231,171,119,227,120,133,179,127,243, 95,131, 10,243,255,244, 21, 36, 81, 4, 23,210, 15,234, 33,122,
+ 39,151, 65,166,252,114,183, 61, 0, 99,172,177,194, 37, 73,130, 36, 73,141,199,199,143, 31,199,188,121,243, 60,242,208, 59,119,
+238,132, 90,173,222,113,173,249,102,188,197,191, 59,205,181,142,240,159, 59,105, 24, 66,252, 93,155,113, 7,234, 71,171,181,106,
+ 1, 99, 6, 69,180,111,102,228,167, 65, 62,245, 31,119,151,109, 68, 35,110,236, 49,147,231,202, 49, 88,191,121, 12,114,145,235,
+225, 18, 85,244, 88,112,218,186,177,155, 15,191,254, 14,229, 14,215, 75, 72, 79, 87,249,225,207,255,168, 11, 36,170, 6, 76,110,
+209,161,177, 71, 13,127, 77,208, 58, 41, 64,131,157,217,178,213,105,120, 17, 6,131, 1, 22,139, 5, 9, 9,221, 59, 38, 66, 41,
+197,158, 61,123,176,118,237, 90,212,214,214,190,123, 45,130,227, 13,254,221,237,167,116,148,127,144, 86,141, 71,110, 29,219,230,
+ 61,199,235, 36,168,218,153, 30,239,200,254, 22,150, 31, 86,130,103,110,167, 68,127,213, 35,243,255, 25,133,253,216, 90, 88,183,
+ 63, 3,106,117, 63, 67, 85,136,106, 26,228, 59,125,213,220,230, 45,243, 74,235,156,122, 97,192,205, 45, 47, 5,169,180, 36,168,
+185, 19,204, 26, 42,186,193,217,106, 72, 66,212,240, 57,113,226, 4,238,185,231, 30,116,215,194, 19, 89,150,177,107,215, 46,124,
+246,217,103,176, 88, 44,142,226,226,226, 45, 6,131, 33, 60, 56, 56,248,230,234,234,234, 35,157,173,190,158,230, 79,105,183,250,
+132, 93,226,255,200,140, 49, 88,179,235, 68,227,130,156,150,152,192, 95,132,121,227, 98, 8, 35,102, 67,125,195, 29, 32,129,117,
+ 19,227,152,104,133,227,226, 62,148, 30,222,128, 16, 91,126, 91, 83, 39, 77, 50, 47,175,244,184,236,139, 86,216,118,189, 2,169,
+224,144,115, 67,205,171,193,192,156,124, 0, 90,219, 20, 29, 31, 18,174,193,129, 54, 18,161,140,111,152, 8,232, 98,108,193,223,
+108,111, 60, 41, 52,111,125, 26, 42,188,249, 75,176, 88, 44, 56,127,254, 60, 94,121,229,149,107,239,226, 36, 9, 63,252,240, 3,
+214,174, 93, 11,155,205,102,191,122,245,234,214,162,162,162,100, 74,105, 49,207,243, 70, 89,150, 75,174,165,245,236, 41,254,255,
+ 90,191, 3, 16, 98,187,189,245,119,197,223, 84,107,198,169,220, 43,184,243, 87, 75,177,249,240,121, 28,207, 43, 70,218,185, 66,
+156,184,100,132, 67,114,223,194,223, 20, 84, 9,106, 42,130, 35,227,159,112,100,252,179, 46, 98, 66, 56, 48, 42,131,128,181, 59,
+186, 69, 8, 94,136,252,205,145, 98,143, 10,191,189, 22,214,255, 62, 7,217,152,237,252,219,193, 49,240,159,245, 38,236, 71,254,
+ 5, 41,191, 41, 90, 44,149,158,107,252,255,233, 7,238,194,127, 94,217, 6,145,181, 86,225, 80,149,132,217,183,212,141,112,203,
+165,173,179, 39, 50, 78, 77,157,194,160, 45, 95, 64,243, 23,113,234,212, 41, 36, 36, 36,224, 90,114, 76, 58, 28, 14,124,255,253,
+247, 88,183,110, 29, 28, 14,135,173,168,168, 40,185,168,168,232,123,142,227,140,140, 49,163, 36, 73,198,170,170,170,210,107,105,
+145,123,146,255, 85, 41,226, 52,250,224,230,238,142,246,184,226,159,125,250, 52,134,198, 77,192, 15, 89,133,216,118,244, 34,174,
+ 86,214,118,232,158, 55, 5, 87,180, 50, 51,192,104,135, 38,203, 51,134,191,233,150, 29,250,196,147,194, 79,173,149,117, 38, 79,
+153,115,170, 33, 97,144, 30,126, 51, 94, 4,209, 4, 66, 24,156,232,164, 0,114,121, 30,236,103,191,135,102,212, 93, 24, 53, 50,
+ 14,219,127, 99,196, 67,255, 76, 69,177,189,105,237,198,208, 0, 59, 62, 91, 58, 3,177,177,117,169, 93,172, 39,190,108,249,211,
+162, 57,192, 97,115, 82,128, 6,123,179,229, 11,144,101, 25, 89, 89, 89,120,253,245,215,187,244,144,118,187, 29,223,126,251, 45,
+214,175, 95, 15, 89,150,109,133,133,133,155,141, 70,227, 14,198,152, 17,128,145,231,121, 99,121,121,185,241, 90, 43,179,167,249,
+ 91,198,207,187, 25,232, 62, 5,104,139,127,118,214,105,188,254,250,235, 24, 61,122, 52,254,186,120, 6, 14,157, 47, 66,114,198,
+121,108,205, 56,143,194, 10,215,202, 16,163,177, 34, 90,109,235, 98,143,132, 47,117,149,135,158,242,104,203,111,173,130,245,219,
+ 39, 65,171,154, 77,234,227, 4,104,110,126, 12,234, 9,191, 68,195, 8, 53, 63, 48,161,254,255,166,104,144, 53,245, 35,168, 98,
+ 38,128, 11,233,135, 91,111,153,137,203,137,211,177,231,192, 30, 20,149,150, 33, 38,162, 15,110,155, 62, 19, 28,199, 3,140,194,
+146,178, 26,210,149, 99, 45,186, 54,124, 25,179,244,152,197,165, 15,208,210,254,204,203,203, 67,104,104, 40, 70,143, 30,221,169,
+ 7,180, 88, 44, 72, 78, 78,198,134, 13, 27, 64, 41,181, 22, 20, 20,108, 46, 47, 47,223,205, 24, 51, 82, 74,141,130, 32, 24,203,
+202,202,140,232,194, 34,230,182,108,232,158,226, 79,253,195,251,121,194, 7,104,143, 63, 71, 8,244, 35,250, 65, 63,162, 31,254,
+180,232, 86, 28,201,189,138,228,140,243, 72, 62,124, 30, 5,101,213, 78,230, 79, 23, 32,130,177,223,235,150, 29,254, 11, 33,158,
+221,179, 75, 46, 60,234, 36,252, 92,200, 0,248,221,246, 50,248,136, 17, 78,229,184,128, 62,224,251,222, 8,185, 56,171, 89,207,
+ 97,130,233,171,135, 17,112,219, 31,160, 30, 58, 29, 60,207, 99,214,140, 89,173, 76,171,218, 29, 47, 66, 44, 56,220,170,174,193,
+216,159,156,122,156,230,161,183,150, 54,232,153, 51,103, 58, 21, 58,172,173,173,197,230,205,155,177,113,227, 70, 80, 74, 45, 6,
+131,225,155,178,178,178,253,140, 49, 35,207,243, 70,198,152,177,170,170,202,136,174,239, 68,216,102,232,176,167,248,171,180, 33,
+241,221, 37, 34, 93,229, 79, 8, 48,121, 88, 52, 38, 15,139,198,170, 95, 78,195,241, 60, 35, 54,238,203, 64,114,250,105,140, 15,
+236,148, 2, 72,140, 97, 7,227,232,107, 17,203, 50,142, 98,185,231,163, 94,252,160, 68,240,125,199, 64, 46, 57, 11,213,136,217,
+208,232,159,116,154,215,223, 28,154,164,223,194,178,229, 9,128, 54, 57,251,204, 81,139,218,255,174,132,122,232,116, 8, 81,163,
+193,135, 15, 1, 9,208, 65,174,184, 12,185,236, 2, 28,185, 7, 64,171, 91,175,165, 98,192,247,125,150, 29,118, 26,216,115,235,
+ 3,152, 76, 38, 20, 23, 23, 99,198,140, 25,237, 62, 80,117,117, 53,190,254,250,107, 36, 39, 39,131, 82,106,190,114,229,202,230,
+178,178,178,131,140, 49, 99,189,157, 95, 28, 26, 26,106,188,120,241,162,221, 35,246,164,194, 31,199,246,124,135,204,228,100, 12,
+161,212,188, 35,219,184,189,223, 56,106,191,101,120,224, 68,157, 63, 63, 26,196,133,233, 79,112,152, 49,178, 94,237,112,124, 21,
+252,236,177,178,158, 12,251, 18,149, 22,254,247,124,220,184, 32,167, 77,101,233,115, 3,212,147, 30,169,115,228, 91,250,102,185,
+251,225,200,221,223,193, 31, 37,121, 2,228, 86,234,237,214, 7,200,206,206,198,157,119,222,217,230,188,153,170,170, 42,124,249,
+229,151, 13,203, 11,107, 13, 6,195,230,170,170,170,180, 6, 27,159, 82,106,212,106,181,198,162,162, 34, 75,101,101,165,199, 42,
+ 84,225,223,154,255,243,151,152, 81,150,139,140,235, 31, 25, 64, 18, 6, 5,106,136, 74,230,136,172, 34, 96, 50, 7,162,170, 10,
+ 95,150, 82, 0,111,131,239, 88, 46, 84,205,132, 95, 1,142, 90, 56, 78,118,121,101,233, 41,153,147,238,212,185,136,106, 53, 42,
+ 64,115, 27, 84, 20, 69,156, 63,127, 30,207, 60,243,140,203,187,149,151,151, 99,253,250,245,216,177, 99, 7,100, 89,174,169,175,
+248,140, 6,161, 81,169, 84,197,140, 49, 99, 69, 69, 69,173,171, 92,239,158, 16, 32,133,191,107,254,119,191,239,203,121,172, 58,
+218,101,112,208, 76,249, 53,248, 62, 55,192,182,255,143, 96, 82,167, 28,252, 20,162, 17,239,138,116, 51,160,215,202, 4, 98,140,
+225,226,197,139, 24, 49, 98, 4,250,245,115,246,245, 74, 74, 74,240,197, 23, 95, 96,247,238,221,144, 36,169,218, 96, 48,108,169,
+174,174, 62,202, 24, 51, 54,216,201, 0,140, 37, 37, 37, 61, 90,235, 10,127,239,242,239, 41, 8,195,102,194,191,223, 68,136,103,
+190,131,120,230, 91, 48,179, 91,203,205, 0, 32,153, 3,217, 18,218,183,127, 74, 91,107, 25, 4,198, 24,107,217, 5, 95,184,112,
+ 1, 79, 61,213, 20, 9, 43, 42, 42,194,231,159,127,142, 3, 7, 14, 64,146, 36, 83,126,126,254,150,218,218,218,147, 13, 81, 17,
+158,231,141,146, 36, 25, 43, 43, 43,123, 60, 91,152, 87,248,203,220, 81,240,244, 53,215,132,136,205,231,249,247, 98,112,218, 48,
+104,110, 90, 12,205,132, 69,117,249,129, 28, 22,124,182,230, 67, 27, 45, 57,179,121, 76, 31,122,118,100,140,176,179,239,242, 35,
+ 29,158, 77, 32, 16, 66,242,171,171,171, 71,134,133,133,129, 82,138,210,210, 82,136,162,136, 41, 83,166,192, 96, 48,224,223,255,
+254, 55,210,210,210, 32,138, 98,229,229,203,151,183,154,205,230,204, 6,231, 16,128, 81,150,101, 99, 85, 85, 85,153,183, 42,196,
+ 27,252,197,205, 43,142, 2, 56,218, 91,249,255,111,104, 2, 15,190, 79,221, 96,215, 57,115,152,188,255,136,120,188,160,160, 96,
+ 91, 85, 85, 85,167, 54,241, 16,236,118,123,106, 73, 73,201,204,254,253,251, 11,148, 82, 92,188,120, 17, 19, 38, 76,192,203, 47,
+191,140, 35, 71,142,192,110,183, 87, 24, 12,134,111,107,107,107,179, 8, 33, 37,168, 91,204, 97,228,121,222, 88, 82, 82, 98,244,
+118, 61, 40,252,189, 15,147,201, 36,100,100,100,120,243,247,121, 66, 8,149,101,185,243,185, 65, 25, 99, 25,121,121,121,246, 33,
+ 67,134, 8,118,187, 29,121,121,121,200,207,207,135,205,102,107,168,248,179,205, 91,155,102,131, 88,212, 23, 42, 95,225,239,117,
+ 24,139,139,139, 79,173, 90,181,138,183,219,237,209,140, 49, 53, 0, 86,159, 97,143, 53,251,160,254, 60,107, 10,203, 59, 95,115,
+119,189,197,189, 90,150,101,178, 44,203,146, 36,149,212,167, 71,236,212, 8, 13, 1,128,105,211,166, 61, 79, 41,125, 11,128,236,
+112, 56,106,138,138,138,182,213,214,214,158,227, 56,174,193,198, 44, 97,140, 21,215, 79, 91,144,224, 99, 80,248,251,134, 81,162,
+211,233,150, 3,232, 91,175,156, 50,234, 18,214, 74,132, 16,153, 49, 38, 19, 66,164,102,231,104,179,107, 13,231,101, 66,136, 84,
+159,228, 86,110,184, 70, 8,145, 41,165, 82,139, 99,185, 33, 35, 52,165, 84,146,101, 89, 98,140, 89,204,102,243,149, 78, 43, 64,
+ 61, 84,225,225,225, 81,140,177, 48,142,227,180, 0,136, 44,203,118,142,227,202,195,195,195, 75, 60, 53, 8,212,141, 80,248,123,
+ 57, 88, 25, 24, 24, 24,205,113,156,154, 16,194, 84, 42, 21, 68, 81,108,108,165, 27, 90,241,230,199,132, 16,218,208,226, 59, 28,
+ 14,167, 30,128, 16,194,154,125, 26,202,194, 98,177, 56,221,131,227, 56, 70, 8, 97,149,149,149,172, 94,233,196,174, 42,128, 2,
+ 5,215,172, 4, 93,181, 4,189, 69,248,255, 3,212, 21,184,121, 66,226, 69,162, 0, 0, 0, 0, 73, 69, 78, 68,174, 66, 96,130,
+};
+
diff --git a/source/blender/src/resources.c b/source/blender/src/resources.c
index 65f44027aee..526cbfab292 100644
--- a/source/blender/src/resources.c
+++ b/source/blender/src/resources.c
@@ -486,8 +486,16 @@ void BIF_InitTheme(void)
/* space imageselect */
btheme->timasel= btheme->tv3d;
+ SETCOL(btheme->timasel.active, 195, 195, 195, 255); /* active tile */
+ SETCOL(btheme->timasel.grid, 94, 94, 94, 255); /* active file text */
SETCOL(btheme->timasel.back, 110, 110, 110, 255);
- SETCOL(btheme->timasel.shade1, 0xaa, 0xaa, 0xba, 255);
+ SETCOL(btheme->timasel.header, 195, 195, 195, 255);
+ SETCOL(btheme->timasel.shade1, 94, 94, 94, 255); /* bar */
+ SETCOL(btheme->timasel.shade2, 172, 172, 172, 255); /* sliders */
+ SETCOL(btheme->timasel.hilite, 17, 27, 60, 100); /* selected tile */
+ SETCOL(btheme->timasel.text, 0, 0, 0, 255);
+ SETCOL(btheme->timasel.text_hi, 255, 255, 255, 255);
+ SETCOL(btheme->timasel.panel, 132, 132, 132, 255);
/* space text */
btheme->text= btheme->tv3d;
@@ -658,7 +666,12 @@ char *BIF_ThemeColorsPup(int spacetype)
str += sprintf(str, "Panel %%x%d|", TH_PANEL);
break;
case SPACE_IMASEL:
- str += sprintf(str, "Main Shade %%x%d|", TH_SHADE1);
+ str += sprintf(str, "Tiles %%x%d|", TH_PANEL);
+ str += sprintf(str, "Scrollbar %%x%d|", TH_SHADE1);
+ str += sprintf(str, "Scroll Handle %%x%d|", TH_SHADE2);
+ str += sprintf(str, "Selected File %%x%d|", TH_HILITE);
+ str += sprintf(str, "Active File %%x%d|", TH_ACTIVE);
+ str += sprintf(str, "Active File Text%%x%d|", TH_GRID);
break;
case SPACE_TEXT:
str += sprintf(str, "Scroll Bar %%x%d|", TH_SHADE1);
diff --git a/source/blender/src/space.c b/source/blender/src/space.c
index e69ed9bf70f..0ec3538abc1 100644
--- a/source/blender/src/space.c
+++ b/source/blender/src/space.c
@@ -110,6 +110,7 @@
#include "BIF_editsima.h"
#include "BIF_editsound.h"
#include "BIF_editview.h"
+#include "BIF_filelist.h"
#include "BIF_gl.h"
#include "BIF_imasel.h"
#include "BIF_interface.h"
@@ -3673,6 +3674,11 @@ void drawinfospace(ScrArea *sa, void *spacedata)
(xpos+edgsp+(2*mpref)+(3*midsp)),y3,(mpref),buth,
&U.recent_files, 0, 30, 0, 0,
"Maximum number of recently opened files to remember");
+
+ uiDefButBitI(block, TOG, USER_SAVE_PREVIEWS, 0, "Save Preview Images",
+ (xpos+edgsp+(3*mpref)+(4*midsp)),y3,mpref,buth,
+ &(U.flag), 0, 0, 0, 0,
+ "Enables automatic saving of preview images in the .blend file");
} else if (U.userpref == 4) { /* system & opengl */
@@ -4657,39 +4663,6 @@ static void init_filespace(ScrArea *sa)
sfile->spacetype= SPACE_FILE;
}
-static void init_imaselspace(ScrArea *sa)
-{
- SpaceImaSel *simasel;
-
- simasel= MEM_callocN(sizeof(SpaceImaSel), "initimaselspace");
- BLI_addhead(&sa->spacedata, simasel);
-
- simasel->spacetype= SPACE_IMASEL;
- simasel->blockscale= 0.7;
- simasel->mode = 7;
- strcpy (simasel->dir, U.textudir); /* TON */
- strcpy (simasel->file, "");
- strcpy(simasel->fole, simasel->file);
- strcpy(simasel->dor, simasel->dir);
-
- simasel->first_sel_ima = 0;
- simasel->hilite_ima = 0;
- simasel->firstdir = 0;
- simasel->firstfile = 0;
- simasel->cmap = 0;
- simasel->returnfunc = NULL;
-
- simasel->title[0] = 0;
-
- clear_ima_dir(simasel);
-
- /* simasel->cmap= IMB_loadiffmem((int*)datatoc_cmap_tga, IB_rect|IB_cmap); */
- simasel->cmap= IMB_ibImageFromMemory((int *)datatoc_cmap_tga, datatoc_cmap_tga_size, IB_rect|IB_cmap);
- if (!simasel->cmap) {
- error("in console");
- printf("Image select cmap file not found \n");
- }
-}
/* ******************** SPACE: SOUND ********************** */
@@ -5009,9 +4982,61 @@ static void init_imagespace(ScrArea *sa)
extern void drawimaselspace(ScrArea *sa, void *spacedata);
extern void winqreadimaselspace(struct ScrArea *sa, void *spacedata, struct BWinEvent *evt);
+static void changeimaselspace(ScrArea *sa, void *spacedata)
+{
+ if(G.v2d==0) return;
-/* everything to imasel.c */
+ test_view2d(G.v2d, curarea->winx, curarea->winy);
+ myortho2(G.v2d->cur.xmin, G.v2d->cur.xmax, G.v2d->cur.ymin, G.v2d->cur.ymax);
+}
+static void init_imaselspace(ScrArea *sa)
+{
+ SpaceImaSel *simasel;
+
+ simasel= MEM_callocN(sizeof(SpaceImaSel), "init imaselspace");
+ BLI_addhead(&sa->spacedata, simasel);
+
+ simasel->spacetype= SPACE_IMASEL;
+ simasel->blockscale= 0.7;
+
+ /* view 2D */
+ simasel->v2d.tot.xmin= -10.0;
+ simasel->v2d.tot.ymin= -10.0;
+ simasel->v2d.tot.xmax= (float)sa->winx + 10.0f;
+ simasel->v2d.tot.ymax= (float)sa->winy + 10.0f;
+
+ simasel->v2d.cur.xmin= 0.0;
+ simasel->v2d.cur.ymin= 0.0;
+ simasel->v2d.cur.xmax= (float)sa->winx;
+ simasel->v2d.cur.ymax= (float)sa->winy;
+
+ simasel->v2d.min[0]= 1.0;
+ simasel->v2d.min[1]= 1.0;
+
+ simasel->v2d.max[0]= 32000.0f;
+ simasel->v2d.max[1]= 32000.0f;
+
+ simasel->v2d.minzoom= 0.5f;
+ simasel->v2d.maxzoom= 1.21f;
+
+ simasel->v2d.scroll= 0;
+ simasel->v2d.keepaspect= 1;
+ simasel->v2d.keepzoom= 1;
+ simasel->v2d.keeptot= 0;
+
+ simasel->prv_h = 96;
+ simasel->prv_w = 96;
+
+ simasel->flag = 7; /* ??? elubie */
+ strcpy (simasel->dir, U.textudir); /* TON */
+ strcpy (simasel->file, "");
+
+ simasel->returnfunc = 0;
+ simasel->title[0] = 0;
+ simasel->type = FILE_UNIX;
+ simasel->files = BIF_filelist_new();
+}
/* ******************** SPACE: OOPS ********************** */
@@ -5496,11 +5521,7 @@ void newspace(ScrArea *sa, int type)
scrarea_queue_headredraw(sa);
addqueue(sa->win, CHANGED, 1);
- scrarea_queue_winredraw(sa);
-
- areawinset(sa->win);
-
- bwin_clear_viewmat(sa->win);
+ scrarea_queue_winredraw(sa);
for (sl= sa->spacedata.first; sl; sl= sl->next)
if(sl->spacetype==type)
@@ -5546,6 +5567,9 @@ void newspace(ScrArea *sa, int type)
sl= sa->spacedata.first;
sl->area= sa;
}
+
+ areawinset(sa->win);
+ bwin_clear_viewmat(sa->win);
}
}
@@ -5567,6 +5591,17 @@ void newspace(ScrArea *sa, int type)
/* exception: imasel space */
else if(sa->spacetype==SPACE_IMASEL) {
SpaceImaSel *simasel= sa->spacedata.first;
+ if(simasel->type==FILE_MAIN) {
+ if (simasel->files) {
+ BIF_filelist_free(simasel->files);
+ BIF_filelist_settype(simasel->files, FILE_MAIN);
+ }
+ } else {
+ if (simasel->files) {
+ simasel->type= FILE_UNIX;
+ BIF_filelist_settype(simasel->files, simasel->type);
+ }
+ }
simasel->returnfunc= NULL;
simasel->title[0]= 0;
}
@@ -5634,7 +5669,8 @@ void freespacelist(ScrArea *sa)
free_oopspace(so);
}
else if(sl->spacetype==SPACE_IMASEL) {
- free_imasel((SpaceImaSel *)sl);
+ SpaceImaSel *simasel= (SpaceImaSel*) sl;
+ free_imasel(simasel);
}
else if(sl->spacetype==SPACE_ACTION) {
free_actionspace((SpaceAction*)sl);
@@ -5701,11 +5737,13 @@ void duplicatespacelist(ScrArea *newarea, ListBase *lb1, ListBase *lb2)
so->treestore= NULL;
}
else if(sl->spacetype==SPACE_IMASEL) {
- check_imasel_copy((SpaceImaSel *) sl);
- }
- else if(sl->spacetype==SPACE_IMAGE) {
- SpaceImage *sima= (SpaceImage *)sl;
- sima->spare= NULL;
+ SpaceImaSel *simasel= (SpaceImaSel*) sl;
+ simasel->pupmenu= NULL;
+ simasel->menup= NULL;
+ simasel->files = BIF_filelist_new();
+ BIF_filelist_setdir(simasel->files, simasel->dir);
+ BIF_filelist_settype(simasel->files, simasel->type);
+ /* see SPACE_FILE - elubie */
}
else if(sl->spacetype==SPACE_NODE) {
SpaceNode *snode= (SpaceNode *)sl;
@@ -6177,7 +6215,7 @@ SpaceType *spaceimasel_get_type(void)
if (!st) {
st= spacetype_new("Imasel");
- spacetype_set_winfuncs(st, drawimaselspace, NULL, winqreadimaselspace);
+ spacetype_set_winfuncs(st, drawimaselspace, changeimaselspace, winqreadimaselspace);
}
return st;
diff --git a/source/blender/src/toets.c b/source/blender/src/toets.c
index 626aec10a2e..6cbc732b847 100644
--- a/source/blender/src/toets.c
+++ b/source/blender/src/toets.c
@@ -73,6 +73,7 @@
#include "BIF_editseq.h"
#include "BIF_editsound.h"
#include "BIF_editmesh.h"
+#include "BIF_imasel.h"
#include "BIF_interface.h"
#include "BKE_object.h"
#include "BIF_poseobject.h"
@@ -466,6 +467,10 @@ int blenderqread(unsigned short event, short val)
activate_fileselect(FILE_LOADLIB, "Load Library", G.lib, 0);
return 0;
}
+ else if(G.qual==LR_CTRLKEY) {
+ activate_imageselect(FILE_LOADLIB, "Load Library", G.lib, 0);
+ return 0;
+ }
break;
case F2KEY:
if(G.qual==0) {
@@ -506,6 +511,15 @@ int blenderqread(unsigned short event, short val)
activate_fileselect(FILE_MAIN, "Data Select", str, NULL);
return 0;
}
+ else if(G.qual==LR_CTRLKEY) {
+
+ memset(str, 0, 16);
+ ob= OBACT;
+ if(ob) strcpy(str, ob->id.name);
+
+ activate_imageselect(FILE_MAIN, "Data Select", str, 0);
+ return 0;
+ }
else if(G.qual==0) {
extern_set_butspace(event, 1);
}
diff --git a/source/blender/src/usiblender.c b/source/blender/src/usiblender.c
index 10fcfeb45aa..38e54d7e456 100644
--- a/source/blender/src/usiblender.c
+++ b/source/blender/src/usiblender.c
@@ -100,6 +100,7 @@
#include "BIF_editmesh.h"
#include "BIF_editmode_undo.h"
#include "BIF_editsound.h"
+#include "BIF_filelist.h"
#include "BIF_poseobject.h"
#include "BIF_previewrender.h"
#include "BIF_renderwin.h"
@@ -626,19 +627,19 @@ static void readBlog(void)
tmps[2]='\\';
tmps[3]=0;
- fsmenu_insert_entry(tmps, 0);
+ fsmenu_insert_entry(tmps, 0, 0);
}
}
/* Adding Desktop and My Documents */
- fsmenu_append_seperator();
+ fsmenu_append_separator();
SHGetSpecialFolderPath(0, folder, CSIDL_PERSONAL, 0);
- fsmenu_insert_entry(folder, 0);
+ fsmenu_insert_entry(folder, 0, 0);
SHGetSpecialFolderPath(0, folder, CSIDL_DESKTOPDIRECTORY, 0);
- fsmenu_insert_entry(folder, 0);
+ fsmenu_insert_entry(folder, 0, 0);
- fsmenu_append_seperator();
+ fsmenu_append_separator();
}
#endif
@@ -649,16 +650,16 @@ static void readBlog(void)
char *line= l->link;
if (!BLI_streq(line, "")) {
- fsmenu_insert_entry(line, 0);
+ fsmenu_insert_entry(line, 0, 1);
}
}
- fsmenu_append_seperator();
+ fsmenu_append_separator();
/* add last saved file */
BLI_split_dirfile(G.sce, name, filename); /* G.sce shouldn't be relative */
- fsmenu_insert_entry(name, 0);
+ fsmenu_insert_entry(name, 0, 0);
BLI_free_file_lines(lines);
}
@@ -884,6 +885,8 @@ void BIF_init(void)
BIF_resources_init(); /* after homefile, to dynamically load an icon file based on theme settings */
+ BIF_filelist_init_icons();
+
init_gl_stuff(); /* drawview.c, after homefile */
readBlog();
BLI_strncpy(G.lib, G.sce, FILE_MAX);
@@ -965,7 +968,9 @@ void exit_usiblender(void)
if (!G.background) {
BIF_resources_free();
-
+
+ BIF_filelist_free_icons();
+
BIF_close_render_display();
mainwindow_close();
}