15 #include "eggTextureCards.h"
18 #include "eggVertexPool.h"
19 #include "eggVertex.h"
20 #include "eggTexture.h"
21 #include "eggPolygon.h"
22 #include "pnmImageHeader.h"
33 EggTextureCards() :
EggWriter(true, true) {
34 set_program_brief(
"generate an .egg file containing texture cards");
35 set_program_description
36 (
"egg-texture-cards generates an egg file consisting of several "
37 "square polygons, one for each texture name that appears on the "
40 "This is a handy thing to have for importing texture images through "
41 "egg-palettize, even when those textures do not appear on any real "
42 "geometry; it can also be used for creating a lot of simple polygons "
43 "for rendering click buttons and similar interfaces.");
46 add_runline(
"[opts] texture [texture ...] output.egg");
47 add_runline(
"[opts] -o output.egg texture [texture ...]");
48 add_runline(
"[opts] texture [texture ...] >output.egg");
51 (
"g",
"left,right,bottom,top", 0,
52 "Specifies the geometry of each polygon. The default is a unit polygon "
53 "centered on the origin: -0.5,0.5,-0.5,0.5. Polygons are always created "
54 "on the X-Y plane. If -p is not also specified, all polygons will be "
55 "the same size and shape.",
56 &EggTextureCards::dispatch_double_quad, NULL, &_polygon_geometry[0]);
59 (
"p",
"xpixels,ypixels", 0,
60 "Indicates that polygons should be sized in proportion to the pixel "
61 "size of the texture image. This will potentially create a "
62 "different size and shape polygon for each texture. The coordinate "
63 "pair represents the image size in "
64 "pixels that will exactly fill up the polygon described with -g (or the "
65 "default polygon if -g is not specified); smaller images will be "
66 "given proportionately smaller polygons, and larger images will be "
67 "given proportionately larger polygons.",
68 &EggTextureCards::dispatch_double_pair, &_got_pixel_scale, &_pixel_scale[0]);
71 (
"suffix",
"string", 0,
72 "Normally, each polygon is given a name based on the basename of its "
73 "corresponding texture's filename (without the filename extension). "
74 "This option specifies an ignorable suffix in the texture filename(s); "
75 "if this suffix is present, it is not included in the polygon's name. "
76 "This option may be repeated multiple times.",
77 &EggTextureCards::dispatch_vector_string, NULL, &_suffixes);
81 "Specifies the color of each polygon. The default is white: 1,1,1,1.",
82 &EggTextureCards::dispatch_color, NULL, &_polygon_color[0]);
86 "Indicates the wrap mode of the texture: \"repeat\", \"clamp\", "
87 "or any of the other modes supported by egg syntax. "
88 "The default is to leave this unspecified.",
89 &EggTextureCards::dispatch_wrap_mode, NULL, &_wrap_mode);
93 "Indicates the wrap mode of the texture in the U direction. This "
94 "overrides -wm, if specified.",
95 &EggTextureCards::dispatch_wrap_mode, NULL, &_wrap_u);
99 "Indicates the wrap mode of the texture in the V direction. This "
100 "overrides -wm, if specified.",
101 &EggTextureCards::dispatch_wrap_mode, NULL, &_wrap_v);
104 (
"minf",
"filter", 0,
105 "Indicates the minfilter mode of the texture: \"linear\", \"mipmap\", "
106 "or any of the other modes supported by egg syntax. "
107 "The default is to leave this unspecified.",
108 &EggTextureCards::dispatch_filter_type, NULL, &_minfilter);
111 (
"magf",
"filter", 0,
112 "Indicates the magfilter mode of the texture: \"linear\" or \"nearest\". "
113 "The default is to leave this unspecified.",
114 &EggTextureCards::dispatch_filter_type, NULL, &_magfilter);
117 (
"aniso",
"degree", 0,
118 "Indicates the anisotropic degree of the texture. "
119 "The default is to leave this unspecified.",
120 &EggTextureCards::dispatch_int, &_got_aniso_degree, &_aniso_degree);
123 (
"ql",
"[default | fastest | normal | best]", 0,
124 "Specifies the quality level of the texture. This mainly affects "
125 "the tinydisplay software renderer.",
126 &EggTextureCards::dispatch_quality_level, NULL, &_quality_level);
130 "Indicates the format for all textures: typical choices are \"rgba12\" "
131 "or \"rgb5\" or \"alpha\". The default is to leave this unspecified.",
132 &EggTextureCards::dispatch_format, NULL, &_format);
136 "Indicates the format for one-channel textures only. If specified, this "
137 "overrides the format specified by -f.",
138 &EggTextureCards::dispatch_format, NULL, &_format_1);
142 "Indicates the format for two-channel textures only. If specified, this "
143 "overrides the format specified by -f.",
144 &EggTextureCards::dispatch_format, NULL, &_format_2);
148 "Indicates the format for three-channel textures only. If specified, this "
149 "overrides the format specified by -f.",
150 &EggTextureCards::dispatch_format, NULL, &_format_3);
154 "Indicates the format for four-channel textures only. If specified, this "
155 "overrides the format specified by -f.",
156 &EggTextureCards::dispatch_format, NULL, &_format_4);
160 "Make the textured polygons backfaced (two-sided).",
161 &EggTextureCards::dispatch_none, &_apply_bface);
164 (
"fps",
"frame-rate", 0,
165 "Normally, all of the texture cards are created as a series of nodes "
166 "beneath a SequenceNode. This allows all of the cards to be viewed, "
167 "one at a time, if the output file is loaded in pview. It also has the "
168 "nice side-effect of creating an automatic texture flip that can be "
169 "used directly by applications; use this parameter to specify the "
170 "frame rate of that texture flip.",
171 &EggTextureCards::dispatch_double, NULL, &_frame_rate);
175 "Don't treat it as an error if the input file references pathnames "
176 "(e.g. textures) that don't exist. Normally, this will be flagged as "
177 "an error and the command aborted; with this option, an egg file will "
178 "be generated anyway, referencing pathnames that do not exist.",
179 &EggTextureCards::dispatch_none, &_noexist);
181 _polygon_geometry.set(-0.5, 0.5, -0.5, 0.5);
182 _polygon_color.set(1.0, 1.0, 1.0, 1.0);
183 _wrap_mode = EggTexture::WM_unspecified;
184 _wrap_u = EggTexture::WM_unspecified;
185 _wrap_v = EggTexture::WM_unspecified;
186 _minfilter = EggTexture::FT_unspecified;
187 _magfilter = EggTexture::FT_unspecified;
189 _quality_level = EggTexture::QL_unspecified;
190 _format = EggTexture::F_unspecified;
191 _format_1 = EggTexture::F_unspecified;
192 _format_2 = EggTexture::F_unspecified;
193 _format_3 = EggTexture::F_unspecified;
194 _format_4 = EggTexture::F_unspecified;
206 bool EggTextureCards::
208 if (!check_last_arg(args, 0)) {
213 nout <<
"No texture names specified on the command line.\n";
217 ProgramBase::Args::iterator ai;
218 for (ai = args.begin(); ai != args.end(); ++ai) {
233 bool EggTextureCards::
234 dispatch_wrap_mode(
const string &opt,
const string &arg,
void *var) {
235 EggTexture::WrapMode *wmp = (EggTexture::WrapMode *)var;
238 if (*wmp == EggTexture::WM_unspecified) {
241 *wmp = EggTexture::WM_repeat;
242 }
else if (arg ==
"c") {
243 *wmp = EggTexture::WM_clamp;
245 nout <<
"Invalid wrap mode parameter for -" << opt <<
": "
262 bool EggTextureCards::
263 dispatch_filter_type(
const string &opt,
const string &arg,
void *var) {
264 EggTexture::FilterType *ftp = (EggTexture::FilterType *)var;
267 if (*ftp == EggTexture::FT_unspecified) {
269 nout <<
"Invalid filter type parameter for -" << opt <<
": "
285 bool EggTextureCards::
286 dispatch_quality_level(
const string &opt,
const string &arg,
void *var) {
287 EggTexture::QualityLevel *qlp = (EggTexture::QualityLevel *)var;
290 if (*qlp == EggTexture::QL_unspecified) {
291 nout <<
"Invalid quality level parameter for -" << opt <<
": "
307 bool EggTextureCards::
308 dispatch_format(
const string &opt,
const string &arg,
void *var) {
309 EggTexture::Format *fp = (EggTexture::Format *)var;
312 if (*fp == EggTexture::F_unspecified) {
313 nout <<
"Invalid format parameter for -" << opt <<
": "
333 bool EggTextureCards::
338 nout <<
"Unable to read image " << filename <<
"\n";
344 double xscale = header.
get_x_size() / _pixel_scale[0];
345 double yscale = header.
get_y_size() / _pixel_scale[1];
347 geometry.set(_polygon_geometry[0] * xscale,
348 _polygon_geometry[1] * xscale,
349 _polygon_geometry[2] * yscale,
350 _polygon_geometry[3] * yscale);
360 void EggTextureCards::
371 (
LPoint3d(geometry[0], geometry[3], 0.0));
373 (
LPoint3d(geometry[0], geometry[2], 0.0));
375 (
LPoint3d(geometry[1], geometry[2], 0.0));
377 (
LPoint3d(geometry[1], geometry[3], 0.0));
390 void EggTextureCards::
397 _data->add_child(group);
402 if (_texture_names.size() > 1) {
403 group->set_switch_flag(
true);
404 group->set_switch_fps(_frame_rate);
412 if (!_got_pixel_scale) {
416 make_vertices(_polygon_geometry, vpool, v1, v2, v3, v4);
421 vector_string::const_iterator ti;
422 for (ti = _texture_names.begin(); ti != _texture_names.end(); ++ti) {
427 vector_string::const_iterator si;
428 for (si = _suffixes.begin(); si != _suffixes.end(); ++si) {
429 const string &suffix = (*si);
430 int prefix = (int)name.length() - (int)suffix.length();
431 if (prefix > 0 && name.substr(prefix) == suffix) {
432 name = name.substr(0, prefix);
439 bool texture_ok = scan_texture(filename, geometry, num_channels);
444 if (_got_pixel_scale) {
446 make_vertices(geometry, vpool, v1, v2, v3, v4);
448 make_vertices(_polygon_geometry, vpool, v1, v2, v3, v4);
453 tref->set_wrap_mode(_wrap_mode);
454 tref->set_wrap_u(_wrap_u);
455 tref->set_wrap_v(_wrap_v);
456 tref->set_minfilter(_minfilter);
457 tref->set_magfilter(_magfilter);
458 if (_got_aniso_degree) {
461 tref->set_quality_level(_quality_level);
464 switch (num_channels) {
466 tref->set_format(_format_1);
470 tref->set_format(_format_2);
474 tref->set_format(_format_3);
478 tref->set_format(_format_4);
483 if (tref->get_format() == EggTexture::F_unspecified) {
484 tref->set_format(_format);
496 poly->set_color(_polygon_color);
508 if (all_ok || _noexist) {
511 nout <<
"Some textures not found; not generating egg file.\n";
517 int main(
int argc,
char *argv[]) {
static WrapMode string_wrap_mode(const string &string)
Returns the WrapMode value associated with the given string representation, or WM_unspecified if the ...
virtual void parse_command_line(int argc, char **argv)
Dispatches on each of the options on the command line, and passes the remaining parameters to handle_...
This is a four-component point in space.
Defines a texture map that may be applied to geometry.
void set_texture(EggTexture *texture)
Replaces the current list of textures with the indicated texture.
static QualityLevel string_quality_level(const string &string)
Returns the TexGen value associated with the given string representation, or ET_unspecified if the st...
This is the base class for all three-component vectors and points.
This is a two-component point in space.
EggVertex * make_new_vertex()
Allocates and returns a new vertex from the pool.
static Format string_format(const string &string)
Returns the Format value associated with the given string representation, or F_unspecified if the str...
void set_bface_flag(bool flag)
Sets the backfacing flag of the polygon.
The main glue of the egg hierarchy, this corresponds to the <Group>, <Instance>, and <Joint> type nod...
void set_anisotropic_degree(int anisotropic_degree)
Sets the degree of anisotropic filtering for this texture.
static FilterType string_filter_type(const string &string)
Returns the FilterType value associated with the given string representation, or FT_unspecified if th...
The name of a file, such as a texture file or an Egg file.
Any one-, two-, three-, or four-component vertex, possibly with attributes such as a normal...
void write_egg_file()
Writes out the egg file as the normal result of the program.
string get_basename_wo_extension() const
Returns the basename part of the filename, without the file extension.
This is a three-component point in space (as opposed to a three-component vector, which represents a ...
EggNode * add_child(EggNode *node)
Adds the indicated child to the group and returns it.
Generates an egg file featuring a number of polygons, one for each named texture. ...
This is the base class for a program that generates an egg file output, but doesn't read any for inpu...
void set_uv(const LTexCoordd &texCoord)
Replaces the unnamed UV coordinate pair on the vertex with the indicated value.
A collection of vertices.
EggVertex * add_vertex(EggVertex *vertex)
Adds the indicated vertex to the end of the primitive's list of vertices, and returns it...
static Filename from_os_specific(const string &os_specific, Type type=T_general)
This named constructor returns a Panda-style filename (that is, using forward slashes, and no drive letter) based on the supplied filename string that describes a filename in the local system conventions (for instance, on Windows, it may use backslashes or begin with a drive letter and a colon).