1#!/usr/local/bin/perl -w
2#
3# All portions of code are copyright by their respective author/s.
4# Copyright (c) 2004     Avi Yagodnick  <aviy@bezeqint.net>
5# Copyright (c) 2006     mark olesen
6#
7# This program is free software; you can redistribute it and/or modify
8# it under the terms of the GNU General Public License as published by
9# the Free Software Foundation; either version 2 of the License, or
10# (at your option) any later version.
11#
12# This program is distributed in the hope that it will be useful,
13# but WITHOUT ANY WARRANTY; without even the implied warranty of
14# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15# GNU General Public License for more details.
16#
17# You should have received a copy of the GNU General Public License
18# along with this program; if not, write to the Free Software
19# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20#
21# ---------------------------------------------------------------------------
22#
23# Mark Olesen: 2006-01-10
24# Complete code re-write (uses warnings/strict) as all perl code should.
25# The entire program is a set of callbacks for Getopt::Long
26#
27# ---------------------------------------------------------------------------
28use strict;
29use Getopt::Long;
30( my $Script = $0 ) =~ s{^.*/}{};
31
32our ( $VERSION, $DATE ) = do {
33    my ( $ver, $date ) =
34      q{$Id: mrxvtset.pl,v 1.2 2006/02/24 23:51:44 jimmyzhou Exp $} =~
35      m{\s+(\d+\.\d+).*?\s+(\d{4}[-/]\d{2}[-/]\d{2})};
36    $date =~ s{/}{-}g;    # ISO-formatted
37    ( $ver, $date );
38};
39
40my %config = (
41    ## set it to your favourite location you wish
42    pixmap => "/tmp/rxvtpixmap-" . getpwuid($<) . ".xpm",
43);
44
45#
46# conversion of file formats
47#
48sub convert_pixmap {
49    my ($val) = @_;
50    -f $val or return undef;
51
52    return $val if $val =~ /\.(xpm)$/;
53    if ( $val =~ /\.(gif|jpe?g|png)$/i ) {
54	system( convert => $val => $config{pixmap} );
55	chmod 0666 => $config{pixmap};
56	return $config{pixmap};
57    }
58
59    return undef;
60}
61
62#
63# lookup table with the xterm codes
64#
65my %opcode = (
66    title => 0,    # change title and iconName
67    ##  XTerm_name		(0)
68    ##  XTerm_iconName		(1)
69    ##  XTerm_title		(2)
70    ##  XTerm_Color		(4)  /* change colors */
71    cursor    => 12,    # Xterm_Color_cursor: change actual 'Cursor' color
72    pointer   => 13,    # Xterm_Color_pointer: change actual 'Pointer' color
73    highlight => 17,    # XTerm_Color_RV: change actual 'Highlight' color
74    bold      => 18,    # Xterm_Color_BD: change actual 'Bold' color
75    underline => 19,    # Xterm_Color_UL: change actual 'Underline' color
76    ##  XTerm_logfile		(46) /* not implemented */
77    fn => 50,           # Xterm_font: restrict our use to font numbers
78    ##  XTerm_Menu		(10) /* set menu item */
79    pixmap => 20,       # new bg pixmap
80    fg     => 39,       # Xterm_restoreFG: change default fg color
81    bg     => 49,       # Xterm_restoreBG: change default bg color
82    ##  XTerm_dumpscreen	(55) /* dump scrollback and all screen */
83    tabtitle => 60,     # Xterm_tab: change tab title
84    ##  Xterm_tabterm		(62) /* change tab and terminal title */
85    newtab => 63,       # create a new tab with title
86    ##  Xterm_prevtab		(64) /* switch to previous tab */
87    ##  Xterm_nexttab		(65) /* switch to next tab */
88    ##  Xterm_tint		(66) /* change tinting color */
89    ##  Xterm_shade		(67) /* change shade level */
90    ##  Xterm_encode		(68) /* change encoding */
91    tb => 69,           # Xterm_hide: hide/show tabbar
92    ##  Xterm_opacity		(70) /* set opacity level */
93    tabbtn => 71,       # hide/show tabbar buttons
94    tabfg  => 72,       # change active tab fg
95    tabbg  => 73,       # change tabbar/active tab bg
96    itabfg => 74,       # change inactive tab fg
97    itabbg => 75,       # change inactive tab bg
98    trans  => 76,       # toggle transparency
99    left   => 77,       # Xterm_moveleft: move active tab to left
100    right  => 78,       # Xterm_moveright: move active tab to right
101    ##  Xterm_verybold		(79) /* toggle bold font for color text */
102    ##  Xterm_hotkeys		(80) /* toggle hotkeys */
103    ##  Xterm_saveconfig	(81) /* save configuration */
104    ##  Xterm_bgfade		(82) /* set bgfade degree */
105    ##  Xterm_termenv		(83) /* set TERMENV type */
106);
107
108#
109# process high/low/toggle commands
110#
111sub high_low_toggle {
112    my ( $type, $val, $opcode ) = @_;
113
114    print "\033[?${opcode}$val\007"
115      if $val =~ s/^(1|y|t).*$/h/i    # high
116      or $val =~ s/^(0|n|f).*$/l/i    # low
117      or $val =~ s/^$/t/              # toggle
118}
119
120# XTerm OSCs:
121# ESC ] Ps;Pt (ST|BEL)
122# process xterm toggle commands
123sub xterm_osc {
124    my ( $type, $val, $opcode ) = @_;
125
126    # warn "$type <$val>\n";
127    my $op = $opcode || $opcode{$type};
128    if ( defined $op ) {
129        print "\033]${op};$val\007";
130    }
131    else {
132        warn "programming error for xterm_osc '$type'\n";
133    }
134}
135
136# ---------------------------------------------------------------------------
137sub usage {
138    $! = 0;    # clean exit
139    warn @_, "\n" if @_;
140    die << "USAGE";
141usage: $Script  { SETTINGS }
142
143SETTINGS:
144  -fg        COLOR     change foreground color
145  -fg        0-15      change foreground to a particular color index
146  -bg        COLOR     change background color
147  -bg        0-15      change background to a particular color index
148  -cursor    COLOR     change cursor color    (alias: -cr)
149  -pointer   COLOR     change pointer color   (alias: -pr)
150  -bold      COLOR     change bold color      (alias: -bd)
151  -underline COLOR     change underline color (alias: -ul)
152  -highlight COLOR     change highlight (reverse video) color (alias: -rv)
153  -tabfg     COLOR     change active    tab foreground
154  -tabbg     COLOR     change active    tab background
155  -itabfg    COLOR     change inactive  tab foreground (alias: -tabifg)
156  -itabbg    COLOR     change inactive  tab background (alias: -tabibg)
157  -pixmap    FILE      if file is not xpm, uses 'convert'.
158                       Note special names: "none", "full", "tiled"
159                       (NB: full/tiled seem to be broken)
160  -fn        [INDEX]   font number 0-6 or +/-, empty for default
161  -title     STRING    change terminal title and icon name
162  -tabtitle  STRING    change tab title (*)
163  -newtab    STRING    create new tab with title (*)
164  -left                move active tab to left
165  -right               move active tab to right
166  -tb                  toggle tabbar visibility (*)
167  -tbb                 toggle tabbar button visibility (alias: tabbtn) (*)
168  -tr                  toggle transparency (alias: trans) (*)
169  -mb [Y|N|empty]      set, unset or toggle menubar   visibility
170  -sb [Y|N|empty]      set, unset or toggle scrollbar visibility
171
172Change (m)rxvt parameters on the fly.
173NB: 'COLOR' can be a color name or specification
174NB: aterm only supports some options (does not support fg)
175(*) - mrxvt only
176
177version $VERSION ($DATE)
178copyright (c) 2006 Mark Olesen <Mark.Olesen\@ArvinMeritor.com>
179
180USAGE
181}
182
183# ---------------------------------------------------------------------------
184my %opt;
185@ARGV or usage("missing settings");
186GetOptions(
187    \%opt,
188    "help|h" => sub { die "\n"; },    # reverts to usage
189
190    # select fonts by number or relative (-/+)
191    # ---------------
192    "fn:s" => sub {
193	my ( $type, $val ) = @_;
194	if ( $val =~ /^([-+]|\d+)$/ or $val =~ s/^(default|normal)?$// ) {
195	    xterm_osc( $type => "#$val" );
196	}
197    },
198
199    # foreground color - ensure reset screen works
200    # ---------------
201    "fg=s" => sub {
202	my ( $type, $val ) = @_;
203	xterm_osc( fg => $val );
204    },
205
206    # background color - problematic with / without pixmap
207    # ---------------
208    "bg=s" => sub {
209	my ( $type, $val ) = @_;
210
211	## use the direct method if an index was specified
212	if ( $val =~ /^\d+$/ ) {
213	    xterm_osc( bg => $val );
214	}
215	else {
216	    ## let us sneak in pixmaps here too!
217	    my $xpm = convert_pixmap($val);
218
219	    unless ( defined $xpm ) {
220		$xpm = $config{pixmap};
221
222		## cheat - set background color indirectly (via a pixmap)
223		local *FILE;
224		open FILE, ">$xpm"
225		  or warn "Cannot write to pixmap '$xpm'\n"
226		  and return;
227
228		print FILE << "PIXMAP";
229/* XPM */
230static char *rxvtbg[] = {
231/* columns rows colors chars-per-pixel */
232"1 1 1 1",
233"x c $val",
234/* pixels */
235"x"
236};
237PIXMAP
238		chmod 0666 => $xpm;
239		close FILE;
240
241	    }
242	    xterm_osc( pixmap => $xpm );
243	}
244    },
245
246    # background pixmap control
247    # ---------------
248    "pixmap=s" => sub {
249	my ( $type, $val ) = @_;
250	if ( $val eq "none" ) {
251	    xterm_osc( pixmap => "" );
252	}
253	## this part seems to be very broken !
254	elsif ( $val eq "full" ) {
255	    print "\033[m";
256	    xterm_osc( pixmap => ";100x100+50+50;?" );
257	}
258	elsif ( $val eq "tiled" ) {
259	    print "\033[m";
260	    xterm_osc( pixmap => ";;0" );
261	}
262	elsif ( -f $val ) {
263	    my $xpm = convert_pixmap($val);
264	    defined $xpm
265	      or warn "skipping unknown file format\n"
266	      and return;
267
268	    xterm_osc( pixmap => $val ) if -f $val;
269	}
270	else {
271	    warn "skipping non-existent file\n";
272	}
273    },
274
275    #
276    # high/low/toggle
277    #
278    "sb:s" => sub { high_low_toggle( @_, 30 ) },    # scrollbar visibility
279    "mb:s" => sub { high_low_toggle( @_, 10 ) },    # menubar visibility
280
281    #
282    # the following use xterm_osc() directly
283    #
284    (
285	map { ( $_ => \&xterm_osc ) } (
286	    "cursor|cr=s",        # change cursor color
287	    "pointer|pr=s",       # change pointer color
288	    "bold|bd=s",          # change bold color
289	    "underline|ul=s",     # change underline color
290	    "highlight|rv=s",     # change highlight color
291	    "tb",                 # toggle tabbar visibility
292	    "tabbtn|tbb",         # toggle tabbar button visibility
293	    "tabfg=s",            # change active tab fg
294	    "tabbg=s",            # change active tab bg
295	    "itabfg|tabifg=s",    # change inactive tab fg
296	    "itabbg|tabibg=s",    # change inactive tab bg
297	    "trans|tr",           # toggle transparency
298	    "left",               # move active tab to left
299	    "right",              # move active tab to right
300	    "title=s",            # change terminal title and icon name
301	    "tabtitle=s",         # change tab title
302	    "newtab=s",           # create new tab with title
303	)
304    ),
305  )
306  or usage();
307
308# use Data::Dumper;
309# warn Dumper(\%opt);
310
311# --------------------------------------------------------------- end-of-file
312