0% found this document useful (0 votes)
313 views1,149 pages

Realhowto Java 201511

Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
313 views1,149 pages

Realhowto Java 201511

Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 1149

Real's HowTo PDF version

Real's HowTo PDF version

Table of Contents
Real's HowTo PDF version (november 2015)..................................................................................................1

AWT.....................................................................................................................................................................3
java-awt....................................................................................................................................................3
Use the CardLayout manager...................................................................................................................3
Detect which card is visible with a CardLayout......................................................................................6
Use Popups..............................................................................................................................................6
Use a File Dialog.....................................................................................................................................9
Use TrueType font.................................................................................................................................10
Display available fonts...........................................................................................................................11
Font with 3D effect................................................................................................................................11
Use the System Clipboard......................................................................................................................12
Maximize a Frame.................................................................................................................................13
Center a Frame/Dialog...........................................................................................................................15
Close a Frame........................................................................................................................................16
Call events on a Frame from a Panel.....................................................................................................17
Set the small top-left icon on a Frame...................................................................................................19
Prevent a Frame to be resized................................................................................................................20
Embed an image into a Frame...............................................................................................................21
Display a message box...........................................................................................................................23
Display a Splash screen.........................................................................................................................25
Vibrate a Window..................................................................................................................................27
Limit TextField input to numeric value.................................................................................................30
Limit TextField input to a maximum length..........................................................................................31
React to the ENTER key in a Textfield.................................................................................................32
Make the ENTER key act like the TAB key..........................................................................................33
Reset all textfields in one shot...............................................................................................................34
Limit a TextField to Uppercase.............................................................................................................35
Have an ImageButton............................................................................................................................36
Reset a checkbox group.........................................................................................................................39
Set the listbox width..............................................................................................................................40
Align the column in a List.....................................................................................................................41
Have a srolling text display using a List................................................................................................41
Label dynamic resizing..........................................................................................................................42
Make a TextArea "word-wrap"..............................................................................................................44
Synchronize a TextArea versus a Choice..............................................................................................44
Display underlined text..........................................................................................................................45
Display vertical text...............................................................................................................................45
Have Label with many lines..................................................................................................................46
Have a Label with underlined text.........................................................................................................51
Have a Label acting as HTML HREF (URLLabel)...............................................................................52
Display a GIF in a Canvas.....................................................................................................................54
Embed an image into a Frame...............................................................................................................55

i
Real's HowTo PDF version

Table of Contents
AWT
Load several images from a single GIF.................................................................................................57
Load an Image from a JAR file..............................................................................................................58
Load an Image from a JAR file (again).................................................................................................59
Scale an Image.......................................................................................................................................60
Fade an image........................................................................................................................................62
Rotate an image......................................................................................................................................64
Create a scrollable canvas......................................................................................................................67
Use an Image as the Applet background................................................................................................70
Have a simple Image browser................................................................................................................72
Simulate a "mouse over" event to toggle an image...............................................................................75
Hide the mouse cursor...........................................................................................................................77
Make a color transparent........................................................................................................................77
Save an Image as a GIF or JPEG file.....................................................................................................79
Use the same background color as the browser.....................................................................................80
Do simple animation using Images........................................................................................................81
Do simple animation to show "work in progress".................................................................................82
Get the color of a specific pixel.............................................................................................................84
Do "rubber-band" drawing.....................................................................................................................85
Convert RGB value to Hex (to be used in HTML)................................................................................87
Draw a line or set a pixel in my own image..........................................................................................87
Draw dashed line....................................................................................................................................88
Draw a line with a thickness..................................................................................................................89
Draw a pie chart.....................................................................................................................................91
Draw faster rectangles............................................................................................................................94
Get a screen capture and save it as a JPEG............................................................................................95
Detect a double click versus a simple click...........................................................................................95
Detect the mouse button used when clicking.........................................................................................97
Exit an application from a menu (single exit point)..............................................................................98
Trigger a click on a Button....................................................................................................................99
Display a TIF.......................................................................................................................................100
Convert a multi-page TIF into single-page TIF...................................................................................102
Convert many single-page TIF into one multi-page TIF.....................................................................103
Convert an Image to a BufferedImage.................................................................................................104
Detect if a TIF is blank........................................................................................................................105
Convert TIF to PDF.............................................................................................................................108
Convert TIF to JPG..............................................................................................................................110

Date and Time.................................................................................................................................................112


java-date...............................................................................................................................................112
Have year on 4 digits from a Date object............................................................................................112
Get the current Date and Time.............................................................................................................112
Compute days between 2 dates............................................................................................................113

ii
Real's HowTo PDF version

Table of Contents
Date and Time
Get the number of days in a month......................................................................................................115
Validate a date......................................................................................................................................115
Determine the day of the week............................................................................................................117
Add/Substract Day/Month/Year to a Date...........................................................................................118
Get the correct TimeZone on DateFormat...........................................................................................119
Simply format a date as "YYYYMMDD"...........................................................................................120
Compare 2 dates...................................................................................................................................120
Parse a String to obtain a Date/GregorianCalendar object..................................................................121
Use System time to generate unique ID...............................................................................................122
Get the day name.................................................................................................................................122
Find the date format pattern.................................................................................................................123
Get a julian date...................................................................................................................................124
Calculate the age..................................................................................................................................127
Format a duration in milliseconds into a human-readable format.......................................................128
Get the atomic time..............................................................................................................................131
Get a date interval................................................................................................................................133
Determine if a given hour is between an interval................................................................................135
Set the computer clock (JNI)...............................................................................................................137
Get unique numerical id based on the system time..............................................................................138
Get the month (or day) name (localized).............................................................................................138
Detect a leap year.................................................................................................................................139

Environment....................................................................................................................................................141
java-env................................................................................................................................................141
Read environment variables from an application................................................................................141
Read environment variables (JDK1.5).................................................................................................145
Read environment variables (JNI).......................................................................................................146
Use a MAKE file.................................................................................................................................147
Detect the browser/JVM type..............................................................................................................148
Fix the "Wrong magic number" error message....................................................................................150
Use a precompiler "à la C" with Java..................................................................................................150
Determine what are the classes actually used......................................................................................152
Set the memory available to the JVM..................................................................................................153
Generate the Javadoc "en français"......................................................................................................153
Use JDK1.5 new features.....................................................................................................................154
Check the class version........................................................................................................................155
Get the system properties or the JVM uptime.....................................................................................156
Detect if running in a 64bit JVM.........................................................................................................157
Set the default JVM type......................................................................................................................158
Select a particular JRE from the command line...................................................................................159
Get the PID (pure Java solution)..........................................................................................................160
Get the PID (JNI solution)...................................................................................................................161

iii
Real's HowTo PDF version

Table of Contents
Environment
Set default value for Java property or JVM option (system wide)......................................................162
Detect if running in debug mode.........................................................................................................163
Configure Java deployment with properties........................................................................................163
Wrap a Java bean in a COM object (using Sun ActiveX bridge)........................................................167
Query the Windows Registry (reg.exe)...............................................................................................169
Query/Update the Windows Registry (hack).......................................................................................172
Quickly retrieve available Java JVM on a workstation (Windows)....................................................181
Detect if a Windows service is running (capture VBS return code)....................................................182
List currently running processes (Windows).......................................................................................184
Check if a program or process is running (Windows).........................................................................186
Check if a process is running (Windows) using WMIC......................................................................188
Windows registry vs Java JDK/JRE installation.................................................................................189
Get the current Java version from a BAT file......................................................................................190
Get the Windows "My Documents" path.............................................................................................192
Get the Windows Desktop path...........................................................................................................192
Get the Windows Special Folders........................................................................................................194
Create an Internet Shortcut..................................................................................................................195
Detect if running in remote session (Windows)..................................................................................197
Detect if running in a Citrix session (Windows).................................................................................198
Create a Taglet to document database access (Javadoc)......................................................................199
Generate the Javadoc "en français"......................................................................................................203
Document a package using Javadoc....................................................................................................204
Display a comment in a Javadoc..........................................................................................................205
Display XML in a Javadoc..................................................................................................................206
Add a copyright notice to a Javadoc....................................................................................................207
Use a Log file.......................................................................................................................................207
Trace the execution..............................................................................................................................210
Time the execution...............................................................................................................................212
Log information efficiently (with Log4J)............................................................................................213
Change the logging level on-the-fly (Log4J).......................................................................................214
Enable debug log level on OpenSource package(Apache Commons Logging)..................................215
Make a JAR executable.......................................................................................................................216
Application with multiples Jars...........................................................................................................218
Extract a file from a Jar........................................................................................................................218
Determine if running from JAR...........................................................................................................220
Get list of classes in package (in a Jar)................................................................................................221
Add version to Jar packaging...............................................................................................................223
Use ANT to Build a JAR with version/build number..........................................................................225
Include all jars in the classpath definition............................................................................................229
Detect browser type from an Applet....................................................................................................233
Detect if Java is enabled from HTML.................................................................................................234
See the Java Console Window Log (Java plugin)...............................................................................235

iv
Real's HowTo PDF version

Table of Contents
Internationalization........................................................................................................................................236
java-inter..............................................................................................................................................236
Load resources based upon client environment at startup...................................................................236
Load resources dynamically................................................................................................................239
Load resources via a resource file........................................................................................................243
Display "special character" using Unicode..........................................................................................247
Display chinese/japanese characters in an Applet...............................................................................248
Localize a JOptionPane dialog.............................................................................................................249
Validate/Convert a number using the current Locale()........................................................................251
Localize a JFileChooser.......................................................................................................................252
Disable localization..............................................................................................................................255
Generate the Javadoc "en français"......................................................................................................256
Sort an array with international characters..........................................................................................257
Accentuated characters in Properties/ResourceBundle file.................................................................259
Compare accentuated letters................................................................................................................259
Remove accent from letters (ex .é to e)...............................................................................................261
Output accentuated characters to the console......................................................................................265
Get the default character set of the JVM.............................................................................................266
Convert OEM (DOS) file to Ansi (Windows).....................................................................................267
Detect non-ASCII character in a String...............................................................................................268
Get the month (or day) name (localized).............................................................................................269

IO......................................................................................................................................................................271
java-io..................................................................................................................................................271
Redirect output(stdout/stderr) to a frame.............................................................................................271
Redirect printStackTrace() to a String.................................................................................................272
Redirect to NULL device.....................................................................................................................273
Print a text file using the javax.print API............................................................................................274
Print a String using the javax.print API...............................................................................................276
Print text to a printer easily..................................................................................................................278
Print without a Dialog..........................................................................................................................278
Initialize and write to a serial port.......................................................................................................279
Open or close a CD/DVD drive...........................................................................................................279
Get the volume label............................................................................................................................281
Detect the storage device type.............................................................................................................282
Turn on MQ Debug mode....................................................................................................................283
Get faster console output (System.out.println() replacement).............................................................283
Simple input from the keyboard..........................................................................................................285
Output french character to the console................................................................................................286
Clear the console and control attributes...............................................................................................288
Easy keyboard input (JDK1.5).............................................................................................................290
Force keyboard input in CAPS LOCK on...........................................................................................292
Automatic conversion of System.out output........................................................................................293

v
Real's HowTo PDF version

Table of Contents
IO
Execute an external program and capture the output...........................................................................294
Launch the application associated with a file extension......................................................................301
Launch an application from another application.................................................................................302
Start the default browser from an application......................................................................................304
Execute a Windows Shortcut (.lnk).....................................................................................................306
Create a file association with a Java program......................................................................................307
Capture the output from a VBS...........................................................................................................308
Get a return code from a VBS..............................................................................................................310
Execute a CMD file stored in a JAR....................................................................................................311
Open the default file explorer..............................................................................................................312
Read the content of a file.....................................................................................................................313
Read a text file from a Jar....................................................................................................................315
Read a text file from the internet.........................................................................................................318
Extract a file from a Jar........................................................................................................................318
Read a data file with floats...................................................................................................................320
Write to the end of a file......................................................................................................................321
Write "real" ascii file...........................................................................................................................322
Copy a file............................................................................................................................................323
Use a "log file".....................................................................................................................................326
Delete files with a certain extension....................................................................................................327
Insert a line in a file.............................................................................................................................328
Read a file into a variable in one shot..................................................................................................329
Serialize an object to a file...................................................................................................................330
Redirect stdout to a file........................................................................................................................332
Get the "last modified" date from a file...............................................................................................332
Get the file creation time......................................................................................................................332
Check if a file exists.............................................................................................................................333
Detect file (or folder) modification......................................................................................................333
File/directory polling to detect change................................................................................................337
Detect file (or folder) modification (Java 7)........................................................................................338
Get the current directory......................................................................................................................339
Get the "root" of an application...........................................................................................................340
Get the content of a directory with a Filter..........................................................................................340
Get the content of a directory with subdirectories...............................................................................343
Get directory content faster with many files........................................................................................345
Make a directory..................................................................................................................................347
Create a fixed-length file.....................................................................................................................347
Delete a non-empty directory...............................................................................................................347
Create a temporary file.........................................................................................................................348
Get the default character set of the JVM.............................................................................................349
Parse a pathname..................................................................................................................................350
Handle CSV files.................................................................................................................................350

vi
Real's HowTo PDF version

Table of Contents
IO
Convert OEM (DOS) file to Ansi (Windows).....................................................................................352
Close a stream in a try/catch block......................................................................................................353
Rename a file extension.......................................................................................................................354
Remove a file extension.......................................................................................................................356
Remove HTML tags from a file to extract only the TEXT.................................................................356
Get the Mime Type from a File...........................................................................................................359
Sort a directory listing (based on the last modified timestamp)..........................................................364
Sort files by the extension....................................................................................................................365
Filter a directory listing by date...........................................................................................................367
Convert wildcard to a regex expression...............................................................................................368
Shorten a long path..............................................................................................................................369
Force a valid Windows filename.........................................................................................................374
Check if filename is valid....................................................................................................................374
Dump a file to a HEX file....................................................................................................................375
List all files in the classpath or in a Jar................................................................................................377
Handle UTF8 file with BOM...............................................................................................................378
Touch a file..........................................................................................................................................381
Handle Excel files................................................................................................................................382
Create an Excel file (the easy way)......................................................................................................388
Detect if a XLS Excel file contains a macro (using POI)....................................................................389
Create or process PDF files..................................................................................................................390
iText - Create a PDF............................................................................................................................393
Split a PDF file (using iText)...............................................................................................................394
Concatenate PDF files (using iText)....................................................................................................395
Convert TIF to PDF.............................................................................................................................397
Convert HTML to PDF using iText.....................................................................................................399
Convert HTML to PDF using YAHP..................................................................................................401
Convert PNG/JPG/GIF to PDF using iText.........................................................................................403
Print a PDF...........................................................................................................................................404
Extract text from a PDF using Apache Tika........................................................................................405
Create a compressed (ZIP) file............................................................................................................405
Display compressed (ZIP) file content................................................................................................407
Expand the compressed (ZIP) file........................................................................................................408
Emit a beep..........................................................................................................................................409
Emit a tone...........................................................................................................................................409
Play an audio file from an application.................................................................................................411
Produce special sound effect................................................................................................................412
Use the Java Speech API (JSPAPI).....................................................................................................416
Play a Windows sound.........................................................................................................................418

vii
Real's HowTo PDF version

Table of Contents
JDBC................................................................................................................................................................420
java-jdbc...............................................................................................................................................420
Get JDBC driver for major database vendors......................................................................................420
Connect to a database via JDBC-ODBC.............................................................................................420
SELECT data from a table...................................................................................................................422
INSERT data into a table.....................................................................................................................423
MODIFY data in a table......................................................................................................................425
DELETE data in a table.......................................................................................................................425
Test for an empty ResultSet.................................................................................................................426
Get row count from SQL.....................................................................................................................426
Store and retrieve an object from a table.............................................................................................427
Retrieve an Image................................................................................................................................429
Insert an Image.....................................................................................................................................429
Call a stored procedure........................................................................................................................430
Stored procedure with Input/Output parms and a ResultSet................................................................430
Fix incomplete field returned by the ResultSet....................................................................................432
Transfer a ResultSet to a JTable..........................................................................................................432
Detect SQL error or warning...............................................................................................................432
Make DSN-less connection..................................................................................................................434
Select a CharSet when connecting to DBMS......................................................................................435
List tables in a database.......................................................................................................................435
Enable JDBC logging..........................................................................................................................437
Detect if a table exists..........................................................................................................................438
Convert a ResultSet in XML...............................................................................................................439
Display ResultSet data in an HTML Table in Servlet.........................................................................441
Escape special character in a LIKE clause..........................................................................................442
Log the SQL Statements......................................................................................................................442
Insert data in batch mode.....................................................................................................................444
Retrieve large ResultSet.......................................................................................................................446
Handle dates.........................................................................................................................................447
Get current date using JDBC...............................................................................................................449
Insert the current date...........................................................................................................................450
Read Excel worksheet..........................................................................................................................450
Handle Excel files................................................................................................................................452
Connect to an Oracle database with JDBC..........................................................................................459
Connect to Oracle using a connection pool.........................................................................................461
Retrieve the generated keys (JDBC Oracle)........................................................................................464
Debug Oracle JDBC connection..........................................................................................................465
Connect to an Oracle database using Kerberos....................................................................................467
Identify the connected program to an Oracle database........................................................................469
Use a CHAR field in the WHERE clause in a PreparedStatement......................................................470

viii
Real's HowTo PDF version

Table of Contents
JNI/JNA...........................................................................................................................................................473
java-jni.................................................................................................................................................473
Use native code through JNI (HelloWorld).........................................................................................473
Pass string to/from Java to/from C......................................................................................................473
Set the computer clock.........................................................................................................................475
Determine the signature of a method...................................................................................................476
Use arrays.............................................................................................................................................477
Load a DLL..........................................................................................................................................479
Use the MouseWheel...........................................................................................................................480
Throw an exception in JNI...................................................................................................................480
Throw my own exception in JNI.........................................................................................................481
JNI from a Package..............................................................................................................................482
Make a Window stay on top................................................................................................................482
Start JVM from C................................................................................................................................483
Retrieve environment variable (JNI)...................................................................................................484
Get the PID..........................................................................................................................................484
Clear the console, set color and cursor position (JNI).........................................................................485
Call Windows API (Open source solution).........................................................................................488
Detect if a program is running (JNA)..................................................................................................489
Close an external windows program using JNA..................................................................................490
Get Windows Special Folders (JNA)...................................................................................................492

Javascript interaction.....................................................................................................................................494
java-js...................................................................................................................................................494
* Read me *.........................................................................................................................................494
Wake-up a Java applet.........................................................................................................................494
Call a Java method from Javascript.....................................................................................................497
Call a Java method from Javascript using DOM.................................................................................499
Access Java variables from Javascript.................................................................................................499
Call Javascript from a Java applet.......................................................................................................500
Create dynamic HTML from a Java applet..........................................................................................503
Inter-Applets communication across frames.......................................................................................504
Inter-Applet communication across pages...........................................................................................506
Write HTML FORM values from a Java applet..................................................................................508
Detect if an Applet is ready.................................................................................................................509
Read/Write HTML field values from Java..........................................................................................510
Detect if Java is enabled......................................................................................................................512
Detect if Java 1.1 (with event delegation) is available........................................................................512
Access Cookies from a Java Applet.....................................................................................................513
Set Applet PARAM VALUE from Javascript.....................................................................................516
Pass an Array between Java and Javascript.........................................................................................517
Interaction without LiveConnect.........................................................................................................520
Directory listing on the Web server in a Java Applet..........................................................................525

ix
Real's HowTo PDF version

Table of Contents
Javascript interaction
Have a Java button close the browser window....................................................................................528
Detect if cookies are enabled...............................................................................................................528
Display a page after all Applets are loaded.........................................................................................529
Detect browser type from an Applet....................................................................................................530

Servlet/JSP.......................................................................................................................................................533
java-jsp.................................................................................................................................................533
Read me...............................................................................................................................................533
Get servlet parameters..........................................................................................................................533
Servlet with no args.............................................................................................................................534
Set a Cookie from a servlet..................................................................................................................535
Read a Cookie from a servlet...............................................................................................................535
Delete a Cookie from a servlet.............................................................................................................536
Ask a password from a Servlet............................................................................................................536
Talk to a Servlet/JSP from an Applet..................................................................................................537
Test for Cookies support......................................................................................................................538
Display ResultSet data in an HTML Table in Servlet.........................................................................539
Specify the filename to be used for a file sent by a Servlet.................................................................539
Pass information to another servlet/jsp................................................................................................540
Handle PDF output..............................................................................................................................540
Detect if a connection is secured.........................................................................................................541
In a Servlet, check if Form Field is present.........................................................................................541
Get the root dir of a web app...............................................................................................................541
Get Client IP from JSP.........................................................................................................................541
Binary output from a JSP.....................................................................................................................542
Use a connection cache from JSP........................................................................................................543
Read a web application property..........................................................................................................545
Use EJB from JSP................................................................................................................................545
Define a method in a JSP page............................................................................................................546
Precompile JSP page............................................................................................................................546
Get a list of directories from JSP.........................................................................................................547
Use and share a class in JSP pages......................................................................................................548
Get the root dir of a web app...............................................................................................................549
Launch an applet from a JSP...............................................................................................................550
Prevent caching of a JSP output...........................................................................................................550
Launch an external program, capture its output and display it in a JSP..............................................551
Call another EJB..................................................................................................................................553
Keep java files generated from JSP (BEA WLS)................................................................................553
Get the server version (BEA WLS).....................................................................................................553
Quickly create a Web application with BEA WLS.............................................................................554
Nicely display WEB.XML informations.............................................................................................554
Reverse the CLASSLOADER order (BEA)........................................................................................556

x
Real's HowTo PDF version

Table of Contents
Servlet/JSP
Detect change in JSP and recompile (BEA)........................................................................................557
Obtain a remote connection to a DataSource or EJB (Weblogic).......................................................557

Language..........................................................................................................................................................560
java-language.......................................................................................................................................560
*Read me*...........................................................................................................................................560
Obtain from where a Class is loaded...................................................................................................560
Get the class name in a static method..................................................................................................561
Get the current method name...............................................................................................................562
Call a method dynamically..................................................................................................................564
Detect if a package is available............................................................................................................566
Create an Object from a String............................................................................................................567
Get a variable value from the variable name.......................................................................................568
Make methods that have unspecified number of parameters...............................................................569
Create a java source dynamically, compile and call............................................................................570
Launch an application from another application.................................................................................573
Access the enclosing class from an inner class....................................................................................574
Access inner class from outside...........................................................................................................575
Use globally defined constants............................................................................................................576
Serialize an Object...............................................................................................................................577
Serialize an Object over a Socket........................................................................................................579
Easily remove my debugging code......................................................................................................579
Have a Singleton..................................................................................................................................580
Multiple expressions in for loops.........................................................................................................581
Handle the List conflict (java.awt.List/java.util.List)..........................................................................581
Use a generic toString().......................................................................................................................582
Use a Object.clone().............................................................................................................................584
Static field, constructor and exception.................................................................................................585
Use a Label break.................................................................................................................................586
Put printStackTrace() into a String......................................................................................................586
Iterate enum values..............................................................................................................................587
Get fields and values from an Object...................................................................................................588
Use a Hashtable....................................................................................................................................589
Scan the content of a hashtable............................................................................................................590
Sort an array.........................................................................................................................................590
Initialize multidimensional array.........................................................................................................592
Get array upperbound..........................................................................................................................593
Convert a String to an array or an array to a String.............................................................................593
Sort Collection in reverse order...........................................................................................................595
Resize an array.....................................................................................................................................596
Dump array content (JDK1.5)..............................................................................................................597
Initialize a static array..........................................................................................................................598

xi
Real's HowTo PDF version

Table of Contents
Language
Sort an Hashtable.................................................................................................................................599
Eliminate "[unchecked] unchecked call ..." compiler warning............................................................600
Sort on many fields..............................................................................................................................602
Optimize Collection usage...................................................................................................................605
Sort an HashMap..................................................................................................................................606
Get keys corresponding to a value from a Map...................................................................................608
Iterate a Collection and remove an item..............................................................................................609
Count distinct elements in a Vector.....................................................................................................611
Dump the content of a Collection (JDK 1.5).......................................................................................612
Initialize a Collection...........................................................................................................................614
Merge (or add) two arrays into one......................................................................................................616
Define an array (or Map, or ENUM) of functions...............................................................................617
Join a List as a String...........................................................................................................................620
Remove duplicates from a List............................................................................................................621
Convert a Map to a Properties (or vice versa).....................................................................................622
Use an INI file (properties)..................................................................................................................623
Load a properties file...........................................................................................................................625
Accentuated characters in Properties/ResourceBundle file.................................................................626
Have a multi-line value in a properties file..........................................................................................626
Use XML with Properties....................................................................................................................627
Use the Registry to store informations.................................................................................................628
Sort Properties when saving.................................................................................................................629
Resolve environment variable in a property value..............................................................................630

Networking......................................................................................................................................................633
java-net.................................................................................................................................................633
Extract network card address...............................................................................................................633
Get the workstation name/ip................................................................................................................636
Find a port number not in use..............................................................................................................638
Disable DNS caching...........................................................................................................................638
Examine the internal DNS cache.........................................................................................................639
Allow user:password in URL...............................................................................................................642
Encode/Decode to/from Base64..........................................................................................................642
Lookup using MX record to validate mail server................................................................................644
Send an email using the SMTP protocol.............................................................................................654
Check if there is mail waiting..............................................................................................................655
Receive email.......................................................................................................................................657
Send email with an attachment............................................................................................................659
Send email with JavaMail....................................................................................................................666
Send email with authentication (JavaMail)..........................................................................................668
HTML mail with images (JavaMail)...................................................................................................669
Debug a Javamail Program..................................................................................................................672

xii
Real's HowTo PDF version

Table of Contents
Networking
Send email with SMTPS (eg. Google GMail) (Javamail)...................................................................673
Mix plain text and HTML content in a mail........................................................................................675
Read an Outlook MSG file (OpenSource packages)...........................................................................676
Handle EML file with JavaMail..........................................................................................................679
Receive email (and attachment) using IMAP......................................................................................681
Receive email (and attachment) using POP3.......................................................................................684
Debug a HttpURLConnection problem...............................................................................................686
Check if a file was modified on the server..........................................................................................688
Check if a page exists..........................................................................................................................688
Connect through a Proxy.....................................................................................................................690
Identify yourself using HTTP Authentification...................................................................................694
Talk to a CGI/Servlet...........................................................................................................................696
Write/Read cookies using HTTP.........................................................................................................697
Read a text file from the internet.........................................................................................................700
Read a GIF or CLASS from an URL save it locally............................................................................700
Resolve a relative URL........................................................................................................................702
File Size from URL..............................................................................................................................702
Using HTTPS protocol........................................................................................................................703
Fix certificate problem in HTTPS........................................................................................................704
Fetch a page from Google....................................................................................................................706
Upload a file.........................................................................................................................................707
Remove HTML tags from a file to extract only the TEXT.................................................................707
Extract links from an HTML page.......................................................................................................710
Call a web service (generated with BEA ServiceGen)........................................................................712
Do basic authentication when calling a webservice............................................................................714
Have a simple HTTP server.................................................................................................................715
Handle JSON Object............................................................................................................................717
HttpUrlConnection with GZIP encoding.............................................................................................727
Connect through a Proxy.....................................................................................................................730
Have timeout on socket connection.....................................................................................................733
Ping a server.........................................................................................................................................734
Get the Date from server......................................................................................................................735
Use Socket's setSoLinger()..................................................................................................................735
Use Socket's setTcpNoDelay()............................................................................................................736
Find who is connecting to a ServerSocket...........................................................................................736
Transfer a file via Socket.....................................................................................................................737
Check if a document exists in a Sharepoint library.............................................................................739
Delete a document in a Sharepoint library...........................................................................................741
Get a document from a Sharepoint library...........................................................................................743
Put or store a document in a Sharepoint library...................................................................................745
Handle MS Exchange public folders...................................................................................................747

xiii
Real's HowTo PDF version

Table of Contents
Open Source....................................................................................................................................................750
java-os..................................................................................................................................................750
Call Windows API...............................................................................................................................750
Call COM object..................................................................................................................................750
Create entity-relation diagram.............................................................................................................751
Java Remote desktop tool....................................................................................................................752
Create entity-relation diagram.............................................................................................................753
Launch a java program as a Windows EXE file..................................................................................753
Tools to handle CSV files....................................................................................................................755
Tools to handle Excel files...................................................................................................................756
Browse a Queue (JMS/MQ).................................................................................................................763
Convert a .class to .java file (decompiler)...........................................................................................763
Deploy an application as only 1 jar......................................................................................................765
Read an Outlook MSG file..................................................................................................................765
File/directory polling to detect change................................................................................................769
Jansi/Jcurses - Clear the console and control attributes.......................................................................770
Disable Checkstyle from code.............................................................................................................773
Create or process PDF files..................................................................................................................774
iText - Create a PDF............................................................................................................................776
Split a PDF file (using iText)...............................................................................................................777
Concatenate PDF files (using iText)....................................................................................................779
Convert TIF to PDF.............................................................................................................................780
Convert HTML to PDF using iText.....................................................................................................782
Convert HTML to PDF using YAHP..................................................................................................784
Convert PNG/JPG/GIF to PDF using iText.........................................................................................786
Print a PDF...........................................................................................................................................787
Extract text from a PDF using Apache Tika........................................................................................788
Detect and remove blank page in pdf (iText)......................................................................................789

Security............................................................................................................................................................792
java-security.........................................................................................................................................792
Encrypt a password..............................................................................................................................792
Create a checksum...............................................................................................................................797
Get the username..................................................................................................................................801
Get the username using NTLM from a JSP.........................................................................................802
Check if the current user belongs a specific Windows group/role......................................................804
Allow user:password in URL...............................................................................................................804
Input password from the console.........................................................................................................805
Prevent XSS exploit.............................................................................................................................806
Display a simple username/password Dialog from an Applet.............................................................808
Solve "Application blocked by security settings" message with unsigned Applet..............................811

xiv
Real's HowTo PDF version

Table of Contents
String/Number.................................................................................................................................................814
java-stringnumber................................................................................................................................814
*Read me*...........................................................................................................................................814
Convert from type X to type Y............................................................................................................814
Strip certain characters from String.....................................................................................................817
Replace/remove character in a String..................................................................................................818
Replace every occurences of a string within a string...........................................................................819
"Tokenize" a string..............................................................................................................................821
Split a string using String.split()..........................................................................................................827
Optimize String operations..................................................................................................................830
Remove spaces from a String..............................................................................................................832
Test if a String starts with a digit or uppercase letter..........................................................................833
Get InputStream from a String.............................................................................................................833
Easy String padding.............................................................................................................................834
Replace \r\n with the <br> tag.............................................................................................................836
Remove accent from letters (ex .é to e)...............................................................................................836
Apply a mask to a string......................................................................................................................840
Format a String (JDK1.5)....................................................................................................................841
Replace a "\" by "\\".............................................................................................................................842
Substitute tokens in a String................................................................................................................843
Compare accentuated letters................................................................................................................843
Create a String with a fixed length......................................................................................................845
Unquote a String..................................................................................................................................846
Escape HTML special characters from a String..................................................................................846
Unescape HTML special characters from a String..............................................................................849
Detect non-ASCII character in a String...............................................................................................853
Remove HTML tags from a file to extract only the TEXT.................................................................854
Extract links from an HTML page.......................................................................................................857
Convert a byte array to a Hex string....................................................................................................859
Apply proper uppercase and lowercase on a String.............................................................................861
Encode/Decode to/from Base64..........................................................................................................862
Justify string with wordwrap...............................................................................................................864
Shorten a long path..............................................................................................................................865
Ellipse a long string.............................................................................................................................869
Display an ASCII banner.....................................................................................................................870
Convert from type X to type Y............................................................................................................871
Type conversion (JDK1.5)...................................................................................................................874
Round a double....................................................................................................................................875
Display numbers with commas............................................................................................................876
Display numbers in scientific notation................................................................................................877
Display numbers with leading zeroes..................................................................................................879
Get a random number...........................................................................................................................880
Convert an UNSIGNED byte to a JAVA integer................................................................................880

xv
Real's HowTo PDF version

Table of Contents
String/Number
Deal with the big-endian and little-endian order.................................................................................882
Pass an integer by reference.................................................................................................................882
Pass floats as string literals to a method..............................................................................................882
Get random numbers............................................................................................................................883
Convert number to words.....................................................................................................................884
Arithmetic with double........................................................................................................................893
Detect even/odd number......................................................................................................................894
Convert bytes to megabytes.................................................................................................................894
Validate a number................................................................................................................................895
Get a unique identifier.........................................................................................................................896
Validate/Convert a number using the current Locale()........................................................................897
Transform a fraction to a Double.........................................................................................................899
Get short ordinal representation of a number......................................................................................900

Swing................................................................................................................................................................902
java-swing............................................................................................................................................902
*Read me*...........................................................................................................................................902
Change default component font...........................................................................................................902
Repaint problem under the mouse cursor (JDK1.2)............................................................................903
Set the LookAndFeel...........................................................................................................................903
Use any LookAndFeel on any plateform.............................................................................................903
Use a Timer..........................................................................................................................................904
Share ActionEvent handler..................................................................................................................905
Get default values for Swing-based user interface..............................................................................907
Have a systray icon (Windows)...........................................................................................................908
Close a JFrame under condition...........................................................................................................910
Maximize a JFrame..............................................................................................................................911
Capture System.out into a JFrame.......................................................................................................912
Remove the titlebar of JInternalFrame................................................................................................915
Have borders on a JWindow/JFrame...................................................................................................915
Display HTML in a JScrollPane..........................................................................................................915
Use a JOptionPane...............................................................................................................................916
Localize a JOptionPane dialog.............................................................................................................918
Customize a JOptionPane dialog.........................................................................................................920
Localize a JFileChooser.......................................................................................................................920
Select a directory with a JFileChooser.................................................................................................924
Disable the JFileChooser's 'New folder' button...................................................................................925
Validate a filename from a JFileChooser.............................................................................................927
Make a JFrame looks like a JDialog....................................................................................................928
Make a JFrame always visible.............................................................................................................929
Show a JFrame on a specific screen in a dual monitor configuration.................................................930
Make a frame not visible in the taskbar...............................................................................................930

xvi
Real's HowTo PDF version

Table of Contents
Swing
Based on JTextField content, enable or disable a JButton...................................................................931
Apply special filter to a JtextField.......................................................................................................932
Limit JTextField input to a maximum length......................................................................................936
Validate a value on the lostFocus event...............................................................................................937
Force the focus on a JTextfield when a JFrame is created..................................................................939
Stop the beep on JFormattedTextField................................................................................................940
Right justified JTextfield content........................................................................................................941
Set the focus on a particuliar JTextField..............................................................................................941
Make JTextField unselectable..............................................................................................................942
Disable copy paste functionality on JTextField...................................................................................942
Use a JTree to navigate in a site...........................................................................................................944
Expand or collapse a JTree..................................................................................................................951
Have a popup attached to a JTree........................................................................................................954
Traverse a JTree...................................................................................................................................956
Dotted Lines in a JTree........................................................................................................................958
Explore directories with a JTree..........................................................................................................958
Prevent JTree collapsing......................................................................................................................960
Single selection in a JTree...................................................................................................................960
Reduce JTree children indentation.......................................................................................................961
Use + or - for JTree Icons....................................................................................................................961
Change JTable header color.................................................................................................................963
Detect doubleclick on a JTable............................................................................................................964
Read a data file into a JTable...............................................................................................................966
Disable row selection in a JTable........................................................................................................969
Detect a data file modification and reload a JTable.............................................................................969
Hide a column in JTable......................................................................................................................971
Scroll a JTable to the last row..............................................................................................................973
Transfer a ResultSet to a JTable..........................................................................................................973
Have on a JScrollPane/JTable an horizontal JScrollbar......................................................................974
Make a JList select an item on doubleclick or the ENTER key..........................................................974
Make a JList like a scrolling text display.............................................................................................976
Have images in a JList.........................................................................................................................977
Add a row and clear a JList..................................................................................................................980
Sort a JList...........................................................................................................................................981
Double click on a JList........................................................................................................................982
Have a PopUp on a JList......................................................................................................................984
Make a JLabel selectable via the mouse..............................................................................................985
Change JLabel background color.........................................................................................................986
Bold/UnBold a JLabel.........................................................................................................................986
Multi-line JLabel..................................................................................................................................987
Underline in Swing..............................................................................................................................987
Update a JLabel....................................................................................................................................988

xvii
Real's HowTo PDF version

Table of Contents
Swing
Display a blinking JLabel....................................................................................................................988
Set the cursor position in a JTextArea.................................................................................................990
Have Multi-line string in a JToolTip...................................................................................................990
Change Tooltip color...........................................................................................................................991
Change a JTooltip font.........................................................................................................................991
Keep a JTooltip visible........................................................................................................................992
Display icon associated with an executable.........................................................................................993
Have items in JMenubar at rightmost position....................................................................................995
Have an JButton with an Image...........................................................................................................996
Trigger a click on a Button..................................................................................................................997

Thread..............................................................................................................................................................999
java-thread............................................................................................................................................999
Pipe the output of a thread to the input of another one........................................................................999
Pipe the output of a thread to the input of other threads....................................................................1001
Wait the for the completion of one thread.........................................................................................1004
Control a thread from outside............................................................................................................1005
Create a Timer object.........................................................................................................................1005
Pause the execution............................................................................................................................1007
Execute a method at regular interval.................................................................................................1007
Execute a process at regular interval.................................................................................................1009
Handle concurrent read/write.............................................................................................................1010
Communicate between threads using a Queue..................................................................................1012
Get a unique identifier.......................................................................................................................1017

Varia...............................................................................................................................................................1020
java-varia............................................................................................................................................1020
Use System time to generate unique ID.............................................................................................1020
Get a unique identifier.......................................................................................................................1020
Get the hard disk serial number or Motherboard Serial number.......................................................1022
Sort an array 1....................................................................................................................................1024
Sort an array 2....................................................................................................................................1026
Do a selection sort..............................................................................................................................1029
Validate a Social Security Number (canadian)..................................................................................1029
Validate a Credit Card Number.........................................................................................................1031
Obtain from where a Class is loaded.................................................................................................1035
Get the class name with or without the package................................................................................1036
See the generated bytecode................................................................................................................1037
Self-replicating programs...................................................................................................................1040
A curiosity..........................................................................................................................................1041
Common Bugs...................................................................................................................................1043
Number of the beast! :-).....................................................................................................................1044

xviii
Real's HowTo PDF version

Table of Contents
Varia
Use Java scripting engine (JDK 1.6)..................................................................................................1044
Pass or retrieve values from a scripting engine (JDK 1.6)................................................................1045
Preventing multiple instances of an application................................................................................1048
Trap JVM shutdown..........................................................................................................................1052
Minimize all programs on Windows to show the Desktop................................................................1052
Display a progress indicator in the console.......................................................................................1053

XML...............................................................................................................................................................1055
java-xml.............................................................................................................................................1055
Read me.............................................................................................................................................1055
Display XML using plain HTML......................................................................................................1056
Transform XML into HTML using XSLT.........................................................................................1057
Parse using SAX or DOM..................................................................................................................1059
Parse an XML string..........................................................................................................................1061
Create an XML document with DOM...............................................................................................1063
Attach a stylesheet to an XML file....................................................................................................1064
Create an XML file and attach an XSL.............................................................................................1065
Nicely display WEB.XML informations...........................................................................................1068
Serialize an object using XML..........................................................................................................1070
Convert flat file to XML using SAX.................................................................................................1071
Convert flat file to XML using DOM................................................................................................1073
Convert a ResultSet in XML.............................................................................................................1076
Parse with XPath................................................................................................................................1078
Strip extra spaces in a XML string....................................................................................................1082
Create an XML file and attach an XSL.............................................................................................1083
Use XML with Properties..................................................................................................................1087
Change a particular node in XML.....................................................................................................1088
Validate XML using a DTD..............................................................................................................1089
Validate XML using a XSD (XML schema).....................................................................................1093
Sanitize XML String..........................................................................................................................1099
Produce HTML entities when using XSLT.......................................................................................1100
Transform XML into CSV using XSLT............................................................................................1100
Create a RSS feed (part 1).................................................................................................................1102
Create a RSS feed (part 2).................................................................................................................1108
Parse a RSS XML file........................................................................................................................1115
Add a Live bookmark........................................................................................................................1117
Validate a RSS feed...........................................................................................................................1117
Attach a CSS to RSS feed..................................................................................................................1118
Handle JSON Object..........................................................................................................................1119

xix
Real's HowTo PDF version (november 2015).
This is the PDF version of the Real's HowTo Web site ( http://www.rgagnon.com/howto.html ). For
up-to-date content, please refer to the Web site. There are 4 files : Real's Java , Real's Javascript, Real's
Powerbuilder and Real's VBS and Misc Prog HowTo. Please don't make PDF versions available on the
internet (it's ok in intranet). From the PDF, you can't run the examples and the links to other How-to's are not
working.

If you feel that effort has been useful to you, perhaps you will consider giving something back? You can make
a donation through PayPal at https://www.paypal.com , make you donation to [email protected]
Contributions via PayPal are accepted in any amount using a credit card or checking account.

(Donations of any size gladly accepted)

This site is covered by the Creative Commons by-nc-sa license :


You can share, adapt and reuse but not for commercial reason. See the FAQ

Real's Howto copyright notice ( [email protected] )

Redistribution and use in source and binary forms,


with or without modification, are permitted provided
that the following conditions is met:

* the source code is used in a development project

Redistributions of source code or site content


(even partially) in any publications (electronic or paper)
is forbidden without permission.

DISCLAIMER

THIS CONTENT IS PROVIDED BY Real Gagnon "AS IS" AND ANY


EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
Real Gagnon BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

Real's HowTo PDF version (november 2015). 1


Real's HowTo PDF version

Real's HowTo PDF version (november 2015). 2


AWT
java-awt

Use the CardLayout manager


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0237.html

A CardLayout object is a layout manager for a container. It treats each component in the container as a card.
Only one card is visible at a time, and the container acts as a stack of cards.

In this HowTo, when a button is clicked the corresponding card is made visible.

First we define the cards (which are based on a Panel)

import java.awt.Color;
import java.awt.Dimension;
import java.awt.LayoutManager;
import java.awt.Panel;

class MyPanel extends Panel{

private static final long serialVersionUID = 1L;


int w;
int h;

MyPanel(Color co, LayoutManager la, int width, int height){


super();
w = width;
h = height;

AWT 3
Real's HowTo PDF version

setBackground(co);
setLayout(la);
}

public Dimension getMinimumSize() {


return new Dimension(w,h);
}

public Dimension getPreferredSize() {


return new Dimension(w,h);
}
}

and then

import java.applet.Applet;
import java.awt.Button;
import java.awt.CardLayout;
import java.awt.Choice;
import java.awt.Color;
import java.awt.Component;
import java.awt.FlowLayout;
import java.awt.Panel;
import java.awt.TextField;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

public class CardLayoutDemo extends Applet


implements ActionListener{

private static final long serialVersionUID = 1L;


Panel p1,p2,p3,p0;
Choice c1,c2;
Button b1,b2,b3, b4;
TextField t1, t2;

public void init() {


// The first Card
p1 = new MyPanel(Color.red,
new FlowLayout(),
100,100) ;
Choice c1 = new Choice();
c1.addItem("Option 1");
c1.addItem("Option 2");
p1.add(c1);

// The second Card


p2 = new MyPanel(Color.blue,
new FlowLayout(),
100, 100);
c2 = new Choice();
c2.addItem("Option A");
c2.addItem("Option B");

Use the CardLayout manager 4


Real's HowTo PDF version

c2.addItem("Option C");
p2.add(c2);

// the third Card


p3 = new MyPanel(Color.black,
new FlowLayout(),
100, 100);
t1 = new TextField(8);
t1.setBackground(Color.white);
p3.add(t1);

// Main card (receive the other)


p0 = new MyPanel(Color.white,
new CardLayout(0,0),
100,100);
setLayout(new FlowLayout());
add(p0);

// Add cards
p0.add("First card", p1);
p0.add("2nd card", p2);
p0.add("3rd card", p3);

add(b1 = new Button("card 1"));


add(b2 = new Button("card 2"));
add(b3 = new Button("card 3"));
add(b4 = new Button("Which card is selected ?"));
add(t2 = new TextField(2));
b1.addActionListener(this);
b2.addActionListener(this);
b3.addActionListener(this);
b4.addActionListener(this);
}

public void actionPerformed(ActionEvent e) {


if (e.getSource() == b1) {
//Show the first
((CardLayout)p0.getLayout()).show(p0, "First card");
}
else if (e.getSource() == b2) {
//Show the second
((CardLayout)p0.getLayout()).show(p0, "2nd card");
}
else if (e.getSource() == b3) {
//Show the third
((CardLayout)p0.getLayout()).show(p0, "3rd card");
}
else if (e.getSource() == b4) {
// get the current card
Component c[] = p0.getComponents();
int i = 0;
int j = c.length;
while (i < j) {

Use the CardLayout manager 5


Real's HowTo PDF version

if (c[i].isVisible()) {
t2.setText("" + (i+1));
break;
}
else
i ++;
}
}
}
}

<HTML>
<TABLE><TR><TD>
<APPLET CODE=CardLayoutDemo.class WIDTH=300 HEIGHT=300>
</APPLET>
&LT;/HMTL&GT;

Try it here.

Detect which card is visible with a CardLayout


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0423.html

Component getComponentShowing(Container c) {
Component[] comps = c.getComponents();
int i = 0;
while(i < comps.length && !comps[i].isVisible())
++i;
return (i == comps.length) ? null : comps[i];
}

Use Popups
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0238.html

[JDK1.1]

import java.awt.*;
import java.awt.event.*;
import java.util.Hashtable;

public class PopupTest extends Frame


implements ActionListener, MouseListener {

Detect which card is visible with a CardLayout 6


Real's HowTo PDF version

Hashtable popupTable = new Hashtable();

public PopupTest() {
/*
** regular menu
*/
Menu m = new Menu("file");
MenuItem item = new MenuItem("file-1");
item.addActionListener(this);
m.add(item);
item = new MenuItem("file-2");
m.add(item);
MenuBar mb = new MenuBar();
mb.add(m);

setMenuBar(mb);
setSize(100, 100);
setLayout(new BorderLayout());

/*
** label with a popup
*/
Label l = new Label("label");
addPopup(l, "label");
add(l, "North");

/*
** panel with popup
*/
Panel p = new Panel();
p.setBackground(new Color(0).red);
addPopup(p, "Panel");
add(p, "Center");

/*
** button with popup
*/
Button b = new Button("button");
addPopup(b, "button");
add(b, "South");

addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);

setVisible(true);
}

public void actionPerformed(ActionEvent e) {


/*

Use Popups 7
Real's HowTo PDF version

** handle actions related to popup


*/
System.out.println("actionPerformed, event=" + e );
System.out.println(" command=" + e.getActionCommand());
System.out.println(" param=" + e.paramString());
System.out.println(" source=" + e.getSource());
}

public void mouseClicked (MouseEvent e) { }


public void mouseEntered (MouseEvent e) { }
public void mouseExited (MouseEvent e) { }
public void mousePressed (MouseEvent e) {
mouseAction(e);
}

public void mouseReleased (MouseEvent e) {


mouseAction(e);
}

void mouseAction (MouseEvent e) {


/*
** determine if we have to show a Popup
*/
Component c = e.getComponent();
if (e.isPopupTrigger()) {
PopupMenu pm = getHash(c);
pm.show(c, c.getSize().width/2, c.getSize().height/2);
}
}

/*
** initialize a Popup for a particular Component
*/

void addPopup(Component c, String name) {


PopupMenu pm = new PopupMenu();
MenuItem mi1 = new MenuItem(name + "-1");
pm.add(mi1);
mi1.addActionListener(this);

MenuItem mi2 = new MenuItem(name + "-2");


pm.add(mi2);
mi2.addActionListener(this);

setHash(c, pm);
c.add(pm);
c.addMouseListener(this);
}

void setHash(Component c, PopupMenu p) {


/*
** associate a Component with a particular Popup
*/

Use Popups 8
Real's HowTo PDF version

popupTable.put(c, p);
}

PopupMenu getHash(Component c) {
/*
** return a Popup associated with a particular Component
*/
return (PopupMenu)(popupTable.get(c));
}

public static void main (String argv[]) {


new PopupTest();
}
}

Use a File Dialog


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0247.html

On the Win platform, the setFilenameFilter method don't work. We must use the setFile method instead to set
a filter.

import java.awt.*;
public class UseFileDialog {

public String loadFile


(Frame f, String title, String defDir, String fileType) {
FileDialog fd = new FileDialog(f, title, FileDialog.LOAD);
fd.setFile(fileType);
fd.setDirectory(defDir);
fd.setLocation(50, 50);
fd.show();
return fd.getFile();
}

public String saveFile


(Frame f, String title, String defDir, String fileType) {
FileDialog fd = new FileDialog(f, title, FileDialog.SAVE);
fd.setFile(fileType);
fd.setDirectory(defDir);
fd.setLocation(50, 50);
fd.show();
return fd.getFile();
}

public static void main(String s[]) {


UseFileDialog ufd = new UseFileDialog();
System.out.println
("Loading : "
+ ufd.loadFile(new Frame(), "Open...", ".\\", "*.java"));

Use a File Dialog 9


Real's HowTo PDF version

System.out.println
("Saving : "
+ ufd.saveFile(new Frame(), "Save...", ".\\", "*.java"));
System.exit(0);
}
}

to work with the full pathname, replace

return fd.getFile();

by

return fd.getDirectory() +
System.getProperty("file.separator") + fd.getFile();

On other plateforms, setFilenameFilter may do the job, then you simply do :

fd.setFilenameFilter(new FilenameFilter(){
public boolean accept(File dir, String name){
return (name.endsWith(".jpg") || name.endsWith(".gif"));
}
});

Use TrueType font


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0270.html

[JDK1.4]
The names of the most common fonts supported by Java are TimesRoman, Courier, and Helvetica. To add
fonts, simply edit the properties.font file located in the lib of your JDK installation.

On a Windows system, to check what are the fonts available, go in the Font applet in the Parameters folder.
Choose a font and doubleclick on it. Check the name of the font. For example, on my system, I have a font
called Kaufmann, the real name is "Kaufmann BT". To be able to use this font, I add the following line in the
properties.font file in the section called # for backword compatibility.

Kaufmann.0=Kaufmann BT, ANSI_CHARSET

To use it, in a java program :

setFont(new Font("Kaufmann", Font.BOLD, 20));

NOTE: The three common fonts are the only ones guaranteed to be supported across all systems. To be able to use other fonts, you must modify the
properties.font file and these new fonts are not cross-plateform compatibles.

Use TrueType font 10


Real's HowTo PDF version

[JDK1.5]
@todo

Display available fonts


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0278.html

[JDK1.1]

import java.awt.*;
public class FontList {
public static void main(String args[]) {
String[] fontNames = Toolkit.getDefaultToolkit().getFontList();
int j = fontNames.length;
for (int i = 0 ; i < j ;i++ ) {
System.out.println(fontNames[i]);
}
}
}

[JDK1.2]

import java.awt.*;
public class FontList {
public static void main(String args[]) {
GraphicsEnvironment ge =
GraphicsEnvironment.getLocalGraphicsEnvironment();
String fontNames[] = ge.getAvailableFontFamilyNames();
int j = fontNames.length;
for (int i = 0 ; i < j ;i++ ) {
System.out.println(fontNames[i]);
}
}
}

Font with 3D effect


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0312.html

import java.awt.*;
import java.applet.*;

public class SimpleApplet extends Applet {

Display available fonts 11


Real's HowTo PDF version

public void init() {


setBackground(new Color(255,255,255)); // white
}

public void paint(Graphics g) {


g.setFont(new Font("Helvetica", Font.PLAIN, 42));
g.setColor(new Color(0,0,0)); // black
g.drawString("Real's HowTo", 100, 100);
g.drawString("Real's HowTo", 101, 101);
g.setColor(getBackground());
g.drawString("Real's HowTo", 100, 100);

g.setColor(new Color(0,0,0)); // black


g.drawString("Real's HowTo", 100, 200);
g.setColor(new Color(0,0,255)); // blue
g.drawString("Real's HowTo", 102, 202);
g.setColor(getBackground());
g.drawString("Real's HowTo", 101, 201);

}
}

<HTML>
<TABLE><TR><TD>
<APPLET CODE=SimpleApplet.class WIDTH=410 HEIGHT=500>
</APPLET>
</HMTL>

try it here

Use the System Clipboard


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0382.html

import java.awt.datatransfer.*;
import java.awt.*;

public class Java2Clipboard implements ClipboardOwner {


public static void main(String[] args) throws Exception {
Java2Clipboard jc = new Java2Clipboard();
jc.toClipboard();
Frame f = new Frame
("Open a text editor and paste the message from Java");
f.setSize(600,10);
f.show();
}

public void toClipboard() {


SecurityManager sm = System.getSecurityManager();

Font with 3D effect 12


Real's HowTo PDF version

if (sm != null) {
try {
sm.checkSystemClipboardAccess();
}
catch (Exception e) {e.printStackTrace();}
}
Toolkit tk = Toolkit.getDefaultToolkit();
StringSelection st =
new StringSelection("Hello world from Java");
Clipboard cp = tk.getSystemClipboard();
cp.setContents(st, this);
}

public void lostOwnership(Clipboard clip, Transferable tr) {


System.out.println("Lost Clipboard Ownership?!?");
}
}

NOTE: You can only use text (no graphic) with this functionality provided by the current JDK (1.4).

Maximize a Frame
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0222.html

// place this in the Frame constructor, after the show()


this.move(0,0);
resize(Toolkit.GetDefaultToolkit().getScreenSize());

JDK1.2 offers a new method, setState(), to minimize or maximize a Frame.

frame.setState(Frame.ICONIFIED); // minimize the frame

Latest JDK provides more ways to do that.

JDK1.4

import java.awt.*;
...
GraphicsDevice device;
Frame frame = new Frame();
device =
GraphicsEnvironment.
getLocalGraphicsEnvironment().
getDefaultScreenDevice();
if ( device.isFullScreenSupported() ) {
device.setFullScreenWindow(frame);
}
else {

Use the System Clipboard 13


Real's HowTo PDF version

System.err.println("Full screen not supported");


}

The "full-screen" Frame is in exclusive mode. In this mode you can change the resolution

import java.awt.*;

class ScreenRes {
public static void main(String args[]) {
new ScreenRes().doit();
}

public void doit() {


Frame frame = new Frame();
GraphicsDevice device;
device =
GraphicsEnvironment.
getLocalGraphicsEnvironment().
getDefaultScreenDevice();
if ( device.isFullScreenSupported() ) {
device.setFullScreenWindow(frame);
if (device.isDisplayChangeSupported()) {
device.setDisplayMode(
new DisplayMode( 1024, 768,
8, // bitDepth - 8 bits 256 colors
DisplayMode.REFRESH_RATE_UNKNOWN ));

}
else {
System.err.println("Change display mode not supported");
}
}
else {
System.err.println("Full screen not supported");
}
}
}

When the JFrame is destroyed, the original resolution is restored.

To remove (manually) the "exclusive mode" on the JFrame :

device.setFullScreenWindow(null);

SWING jdk1.3

JFrame frame = new JFrame();


frame.setExtendedState(Frame.MAXIMIZED_BOTH);
// can be
// frame.setExtendedState(Frame.MAXIMIZED_HORIZ);
// frame.setExtendedState(Frame.MAXIMIZED_VERT);

Maximize a Frame 14
Real's HowTo PDF version

Center a Frame/Dialog
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0223.html

// centers the dialog within the screen [1.1]


// (put that in the Frame/Dialog class)
public void centerScreen() {
Dimension dim = getToolkit().getScreenSize();
Rectangle abounds = getBounds();
setLocation((dim.width - abounds.width) / 2,
(dim.height - abounds.height) / 2);
super.setVsible(true);
requestFocus();
}

// centers the dialog within the parent container [1.1]


// (put that in the Dialog class)
public void centerParent () {
int x;
int y;

// Find out our parent


Container myParent = getParent();
Point topLeft = myParent.getLocationOnScreen();
Dimension parentSize = myParent.getSize();

Dimension mySize = getSize();

if (parentSize.width > mySize.width)


x = ((parentSize.width - mySize.width)/2) + topLeft.x;
else
x = topLeft.x;

if (parentSize.height > mySize.height)


y = ((parentSize.height - mySize.height)/2) + topLeft.y;
else
y = topLeft.y;

setLocation (x, y);


super.setVsible(true);
requestFocus();
}

New with JDK1.4, JDialog has method to position a JDialog relative to a parent. For a JWindow or a JFrame
with no parent, then

f.setSize(100,100);
f.setLocationRelativeTo(NULL);

Center a Frame/Dialog 15
Real's HowTo PDF version

Close a Frame
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0225.html

[JDK1.0.2]

public boolean handleEvent(Event evt) {


if (evt.id == Event.WINDOW_DESTROY) {
System.exit(0);
return true;
}
return super.handleEvent(evt);
}

[JDK1.1 Method 1]

public aFrame extends Frame implements WindowListener {


public aFrame(){
addWindowListener( this );
}
public void windowActivated(WindowEvent e){}
public void windowDeactivated(WindowEvent e){}
public void windowOpened(WindowEvent e){}
public void windowClosing(WindowEvent e){ System.exit(0); }
public void windowClosed(WindowEvent e){}
public void windowIconified(WindowEvent e) {}
public void windowDeiconified(WindowEvent e) {}
}

[JDK1.1 Method 2]

public class aFrame extends Frame {


public aFrame(){
addWindowListener( new Terminate() );
}
}

class Terminate extends WindowAdapter{


public void windowClosing(WindowEvent e){
System.exit(0);
}
}

[JDK1.1 Method 3]

public class aFrame extends Frame {


public aFrame() {
addWindowListener

Close a Frame 16
Real's HowTo PDF version

(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
}
}

For a Dialog or a Window, a System.exit(0) may not be appropriate, call the dispose() method instead.

class SimplePopUp extends Dialog {


SimplePopUp() {
super(new Frame(), "simple popup");
this.addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
e.getWindow().dispose();
}
}
);
}

Call events on a Frame from a Panel


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0268.html

A component on a Panel can easily call events on the parent Frame. This way, we can put all the logic in one
place. In this example, a Frame contains 1 button and a Panel with 2 buttons on it. The first button on the
Panel will generate an event for the button on the Frame while the second panel button will trigger a request to
close the Frame and the application.

[TestEventPanel.java]

import java.awt.*;
import java.awt.event.*;

public class TestEventPanel extends Panel {


Button b1,b2;

TestEventPanel(){
super();
setLayout(new FlowLayout());
setBackground(new Color(0).black);
b1 = new Button("call event on the frame");
add(b1);
b2 = new Button("close the parent frame");
add(b2);

Call events on a Frame from a Panel 17


Real's HowTo PDF version

}
}

The Frame after adding the Panel, will act as an ActionListener for events for the 2 Panel buttons.

[TestEventFrame.java]

import java.awt.*;
import java.awt.event.*;

public class TestEventFrame extends Frame implements


ActionListener, WindowListener {
TestEventPanel p1;
Button b1;

TestEventFrame(String title){
super(title);
setLayout(new FlowLayout());
p1 = new TestEventPanel();

b1 = new Button("A dummy button");


add(b1);

// the Panel with 2 buttons on it


add(p1);
createFrame();

// add the actionlistener


b1.addActionListener(this);
p1.b1.addActionListener(this);
p1.b2.addActionListener(this);
addWindowListener(this);
}

void createFrame() {
Dimension d = getToolkit().getScreenSize();
setLocation(d.width/4,d.height/3);
setSize(400,100);
setVisible(true);
}

public void actionPerformed(ActionEvent ae){

if (ae.getSource()==p1.b1) {
System.out.println(ae.getActionCommand());
ActionEvent new_ae =
new ActionEvent (b1,
ActionEvent.ACTION_PERFORMED,
"Panel b1 is calling the dummy button");
b1.dispatchEvent (new_ae);
}

if (ae.getSource()==b1) {

Call events on a Frame from a Panel 18


Real's HowTo PDF version

System.out.println("dummy receive :" + ae.getActionCommand());


}

if (ae.getSource()==p1.b2) {
System.out.println(ae.getActionCommand());
processEvent(new WindowEvent(this, WindowEvent.WINDOW_CLOSING));
}

public void windowClosing(WindowEvent e) {


this.dispose();
System.exit(0);
}
public void windowActivated(WindowEvent e) { }
public void windowDeactivated(WindowEvent e) { }
public void windowDeiconified(WindowEvent e) { }
public void windowClosed(WindowEvent e) { }
public void windowIconified(WindowEvent e) { }
public void windowOpened(WindowEvent e) { }
}

and finally

[Java0268.java]

import java.awt.*;

public class Java0268 extends java.applet.Applet {


TestEventFrame myTestEventFrame;

public void init() {


myTestEventFrame =
new TestEventFrame("TestEvent Frame");
}
}

Try it here.

Set the small top-left icon on a Frame


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0246.html

There is a bug in JDK1.0.2 for Windows, so you are stuck with the JAVA coffee cup.

In JDK1.1, this is fixed. You have to use a GIF file (not ICO file!). The GIF dimension should be 16x16. With
1.5, you can use a PNG or JPG file.

Set the small top-left icon on a Frame 19


Real's HowTo PDF version

You set the icon with :

frame.setIconImage(Toolkit.getDefaultToolkit().getImage("myIcon.gif"));

To get the image from a Jar instead, do :

frame.setIconImage
(Toolkit.getDefaultToolkit()
.getImage(getClass().
getResource("images/myIcon.gif")));

or

frame.setIconImage(
new ImageIcon(
YourApp.class.getResource("logo.png")
).getImage()
);

Prevent a Frame to be resized


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0252.html

import java.awt.*;
import java.awt.event.*;

public class TestNoMaximize {


MyFrame theFrame;

public static void main (String args[]){


TestNoMaximize t = new TestNoMaximize();
t.theFrame = new MyFrame("A Dummy Frame");
t.theFrame.setVisible(true);
}
}

class MyFrame extends Frame {


public MyFrame(String title){
super(title);
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
// no minimize or maximize

Prevent a Frame to be resized 20


Real's HowTo PDF version

this.setResizable(false);
this.setSize(200,200);
}

public void paint(Graphics g) {


g.drawString("try to resize me...", 50, 50);
}
}

There is no way to allow minimizing but not maximizing unless you trap the maximizing in the paint method
and then resize to the original size.

import java.awt.*;
import java.awt.event.*;

public class TestNoMaximize {


MyFrame theFrame;

public static void main (String args[]){


TestNoMaximize t = new TestNoMaximize();
t.theFrame = new MyFrame("A Dummy Frame");
t.theFrame.setVisible(true);
}
}

class MyFrame extends Frame {


public MyFrame(String title){
super(title);
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
this.setSize(200,200);
}

public void paint(Graphics g) {


Dimension d = this.getSize();
if (d.getHeight() != 200 && d.getWidth() != 200)
this.setSize(200,200);
g.drawString("try to maximize me...", 50, 50);
}
}

NOTE: These How-to may not work with the Microsoft JVM. It's a feature...

Embed an image into a Frame


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0302.html

Embed an image into a Frame 21


Real's HowTo PDF version

A given image is tiled as the frame background.

The result is not too good with Label...

import java.awt.*;
import java.awt.event.*;

public class ImageFrame extends Frame {

private Image image;

ImageFrame() {
super("");
try {
MediaTracker mt = new MediaTracker (this);
// for Applet, change the method to retrieve the image
// and of course use your own image!
image = Toolkit.getDefaultToolkit().getImage("images/jht.gif");
mt.addImage(image, 0);
mt.waitForID(0);
}
catch (Exception e) {
e.printStackTrace();
}

setLayout(new FlowLayout());

add(new TextField(10));
add(new Button("hello"));
add(new List(20));
add(new TextArea(20,20));
// Label may not look too good ...
add(new Label("Hello"));
setSize(500, 500);

addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
// change this for an Applet
System.out.println("Bye.");
System.exit(0);
}
}
);
}

public void update( Graphics g) {


paint(g);
}

public void paint(Graphics g) {


if(image != null) {

Embed an image into a Frame 22


Real's HowTo PDF version

int x = 0, y = 0;
while(y < getSize().height) {
x = 0;
while(x< getSize().width) {
g.drawImage(image, x, y, this);
x= x + image.getWidth(null);
}
y = y + image.getHeight(null);
}
}
else {
g.clearRect(0, 0, getSize().width, getSize().height);
}
}

static public void main(String[] args) {


ImageFrame iframe = new ImageFrame();
iframe.setVisible(true);
}
}

The result :

Display a message box


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0242.html

Display a message box 23


Real's HowTo PDF version

If using Swing then look at the JOptionPane component.

With plain AWT, this simple class can be used as a Message Box.

import java.awt.*;
import java.awt.event.*;

public class MsgBox extends Dialog implements ActionListener {


private Button ok,can;
public boolean isOk = false;

/*
* @param frame parent frame
* @param msg message to be displayed
* @param okcan true : ok cancel buttons, false : ok button only
*/
MsgBox(Frame frame, String msg, boolean okcan){
super(frame, "Message", true);
setLayout(new BorderLayout());
add("Center",new Label(msg));
addOKCancelPanel(okcan);
createFrame();
pack();
setVisible(true);
}

MsgBox(Frame frame, String msg){


this(frame, msg, false);
}

void addOKCancelPanel( boolean okcan ) {


Panel p = new Panel();
p.setLayout(new FlowLayout());
createOKButton( p );
if (okcan == true)
createCancelButton( p );
add("South",p);
}

void createOKButton(Panel p) {
p.add(ok = new Button("OK"));
ok.addActionListener(this);
}

void createCancelButton(Panel p) {
p.add(can = new Button("Cancel"));
can.addActionListener(this);
}

void createFrame() {
Dimension d = getToolkit().getScreenSize();
setLocation(d.width/3,d.height/3);

Display a message box 24


Real's HowTo PDF version

public void actionPerformed(ActionEvent ae){


if(ae.getSource() == ok) {
isOk = true;
setVisible(false);
}
else if(ae.getSource() == can) {
setVisible(false);
}
}

public static void main(String args[]){


Frame f = new Frame();
f.setSize(200,200);
f.setVisible(true);
MsgBox message = new MsgBox
(f , "Hey you user, are you sure ?", true);

if (message.isOk)
System.out.println("Ok pressed");

if (!message.isOk)
System.out.println("Cancel pressed");

message.dispose();
}
}

Display a Splash screen


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0267.html

This Splash class display a window containing a specified image while a parent Frame is doing its
initialization. When the parent is activated, the Splash window is destroyed.

[JDK1.1]
import java.awt.*;
import java.awt.event.*;

public class Splash extends Window {


private Image splashImage;
private int imgWidth, imgHeight;
private String imgName;
private static final int BORDERSIZE = 5;
private static final Color BORDERCOLOR = Color.blue;
Toolkit tk;

public Splash(Frame f, String imgName) {


super(f);

Display a Splash screen 25


Real's HowTo PDF version

this.imgName = imgName;
tk = Toolkit.getDefaultToolkit();
splashImage = loadSplashImage();
showSplashScreen();
f.addWindowListener(new WindowListener());
}
public Image loadSplashImage() {
MediaTracker tracker = new MediaTracker(this);
Image result;
result = tk.getImage(imgName);
tracker.addImage(result, 0);
try {
tracker.waitForAll();
}
catch (Exception e) {
e.printStackTrace();
}
imgWidth = result.getWidth(this);
imgHeight = result.getHeight(this);
return (result);
}

public void showSplashScreen() {


Dimension screenSize = tk.getScreenSize();
setBackground(BORDERCOLOR);
int w = imgWidth + (BORDERSIZE * 2);
int h = imgHeight + (BORDERSIZE * 2);
int x = (screenSize.width - w) /2;
int y = (screenSize.height - h) /2;
setBounds(x, y, w, h);
setVisible(true);
}

public void paint(Graphics g) {


g.drawImage(splashImage, BORDERSIZE, BORDERSIZE,
imgWidth, imgHeight, this);
}

class WindowListener extends WindowAdapter {


// was windowActivated, thanks to H.Grippa for the fix!
public void windowOpened(WindowEvent we) {
setVisible(false);
dispose();
}
}
}

The following example use this image (jht.gif) as the splash image.

import java.awt.*;
import java.awt.event.*;

public class TestSplash {


MyFrame theFrame;

Display a Splash screen 26


Real's HowTo PDF version

public static void main (String args[]){


TestSplash t = new TestSplash();
t.createMainFrame();
}

private void createMainFrame() {


theFrame = new MyFrame("A Dummy Frame");
theFrame.setVisible(true);
}

class MyFrame extends Frame {


Splash mySplash;
public MyFrame(String title){
super(title);
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
mySplash = new Splash(this, "jht.gif");

// dummy delay so we can see the Splash!


for(int i = 0; i < 3000; i++) {
System.out.println(i) ;
}
setSize(200,200);
}
}

Vibrate a Window
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0622.html

This HowTo is based on this post : http://sdnshare.sun.com/view.jsp?id=2326

This can be useful to make a visual effect when an event is occuring.

import java.awt.*;

public class FrameUtils {

private final static int VIBRATION_LENGTH = 20;


private final static int VIBRATION_VELOCITY = 5;

Vibrate a Window 27
Real's HowTo PDF version

private FrameUtils() { }

public static void vibrate(Frame frame) {


try {
final int originalX = frame.getLocationOnScreen().x;
final int originalY = frame.getLocationOnScreen().y;
for(int i = 0; i < VIBRATION_LENGTH; i++) {
Thread.sleep(10);
frame.setLocation(originalX, originalY + VIBRATION_VELOCITY);
Thread.sleep(10);
frame.setLocation(originalX, originalY - VIBRATION_VELOCITY);
Thread.sleep(10);
frame.setLocation(originalX + VIBRATION_VELOCITY, originalY);
Thread.sleep(10);
frame.setLocation(originalX, originalY);
}
}
catch (Exception err) {
err.printStackTrace();
}
}
}

To use it, simply pass a Frame to the vibrate method.

FrameUtils.vibrate(myFrame);

To make it more Swing-oriented, you change the method signature for a JFrame instead.

Here an example.

We display a small window. When a file is added or deleted, the window is shaking for a brief moment and
display the event. By default, the folder c:/temp is used but you can specify another one on the command line.

First get the code to detect a file modfication in a folder (in this HowTo, you need the DirWatcher and
DirFilterWatcher classes). Plus the following classes.

import java.awt.*;
import java.awt.event.*;

public class DirWatchWindow extends Frame {


Label folder;
Label info;

public DirWatchWindow() {
setTitle("DirWatchWindow");
setSize(600, 100);
setLayout(new BorderLayout());
folder = new Label("");
info = new Label("");
add(folder, BorderLayout.NORTH);

Vibrate a Window 28
Real's HowTo PDF version

add(info, BorderLayout.SOUTH);
setVisible(true);
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
}

public void setInfo(String text) {


info.setText(text);
}

public void setFolder(String dir) {


folder.setText("Watching folder : " + dir);
}
}

import java.util.*;
import java.io.*;

public class DirWatchTest {

public static void main(String args[]) {


String folderToWatch = "c:/temp";

if (args.length > 0) {
folderToWatch = args[0];
}

final DirWatchWindow dww = new DirWatchWindow();


dww.setFolder(folderToWatch);
TimerTask task = new DirWatcher(folderToWatch, "txt" ) {
protected void onChange( File file, String action ) {
// here we code the action on a change
dww.setInfo("File : "+ file.getName() +" action: " + action);
FrameUtils.vibrate(dww);
}
};

Timer timer = new Timer();


timer.schedule( task , new Date(), 1000 );
}
}

You can download an executable JAR here

To launch the demo

Vibrate a Window 29
Real's HowTo PDF version

java -jar DirWatch.jar

to watch the default directory c:/temp or

java -jar DirWatch.jar c:/myfolder

to specify your own folder. This demo is watching for files with the extension txt only.

Limit TextField input to numeric value


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0226.html

[JDK1.0.2]

// You still have to trap the InvalidNumberFormat


// Exception when converting textfield content to numeric
// bug fixed! 980211 thanks to JM Guerra Chapa
import java.awt.*;
public class app extends java.applet.Applet {
TextField textField1;

public void init() {


setLayout(new FlowLayout());
textField1 = new TextField(10);
add(textField1);
}

public boolean handleEvent(Event event) {


if (event.target==textfield1 && event.id == Event.KEY_PRESS) {
char c = (char)event.key;
if (c >= '0' && c <= '9') {
// keep digit
return super.handleEvent(event);
}
else if (Character.isISOControl(c)) {
// keep control character (like del, bksp)
return super.handleEvent(event);
}
else {
// discard Character
return true;
}
}
return super.handleEvent(event);
}
}

[JDK1.1]

Limit TextField input to numeric value 30


Real's HowTo PDF version

thanks to Lionel Giltay

import java.awt.TextField ;
import java.awt.event.KeyAdapter ;
import java.awt.event.KeyEvent ;

public class NumericTextField extends TextField


{
public NumericTextField (String _initialStr, int _col)
{
super (_initialStr, _col) ;

this.addKeyListener(new KeyAdapter()
{
public void keyTyped (KeyEvent e)
{
char c = e.getKeyChar() ;

if (! ((c==KeyEvent.VK_BACK_SPACE) || (c==KeyEvent.VK_DELETE)
|| (c== KeyEvent.VK_ENTER) || (c == KeyEvent.VK_TAB)
|| (Character.isDigit(c))))
{
e.consume() ;
}
}
});
}

public NumericTextField (int _col)


{
this ("", _col) ;
}
}

Limit TextField input to a maximum length


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0227.html

[JDK11]

import java.awt.*;
import java.awt.event.*;

public class TextFieldWithLimit extends TextField


implements KeyListener {
private int maxLength;
public TextFieldWithLimit
(String initialStr,int col,int maxLength) {
super(initialStr,col);
this.maxLength = maxLength;

Limit TextField input to a maximum length 31


Real's HowTo PDF version

addKeyListener(this);
}
public TextFieldWithLimit (int col,int maxLength) {
this("",col,maxLength);
}

public void keyPressed(KeyEvent e) {


char c = e.getKeyChar();
int len = getText().length();
if (len <maxLength) {
return;
}
else {
if((c==KeyEvent.VK_BACK_SPACE)||
(c==KeyEvent.VK_DELETE) ||
(c==KeyEvent.VK_ENTER)||
(c==KeyEvent.VK_TAB)||
e.isActionKey())
return;
else {
e.consume();
}
}
}
public void keyReleased(KeyEvent e) { }
public void keyTyped(KeyEvent e) { }
}

React to the ENTER key in a Textfield


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0253.html

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

public class testENTER extends Applet


implements KeyListener {
TextField t;
public void init(){
TextField t = new TextField("press ENTER");
add(t);
t.addKeyListener(this);
}
public void keyTyped(KeyEvent e) {}
public void keyReleased(KeyEvent e) {}
public void keyPressed(KeyEvent e) {
int key = e.getKeyCode();
if (key == KeyEvent.VK_ENTER) {

React to the ENTER key in a Textfield 32


Real's HowTo PDF version

Toolkit.getDefaultToolkit().beep();
System.out.println("ENTER pressed");
}
}
}

Or the short version using the KeyAdapter class.

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

public class testENTER extends Applet{


TextField t;
public void init(){
TextField t = new TextField("press ENTER");
add(t);
t.addKeyListener
(new KeyAdapter() {
public void keyPressed(KeyEvent e) {
int key = e.getKeyCode();
if (key == KeyEvent.VK_ENTER) {
Toolkit.getDefaultToolkit().beep();
System.out.println("ENTER pressed");
}
}
}
);
}
}

Make the ENTER key act like the TAB key


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0254.html

First create a TextField that listen to the Enter and react like a Tab key [JDK11]

import java.awt.*;
import java.awt.event.*;

public class MyTextField extends TextField {


MyTextField(int len) {
super(len);
addKeyListener(new KeyAdapter() {
public void keyPressed(KeyEvent evt) {
int key = evt.getKeyCode();
if (key == KeyEvent.VK_ENTER)
transferFocus();}});
}

Make the ENTER key act like the TAB key 33


Real's HowTo PDF version

to use it, try something like this

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

public class TestEnterAsTab extends Applet {


MyTextField t1, t2;
public void init(){
MyTextField t1 = new MyTextField(10);
MyTextField t2 = new MyTextField(10);
add(t1);add(t2);
}
}

Reset all textfields in one shot


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0274.html

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

public class FirstApplet extends Applet implements


ActionListener {
TextField t1;
TextField t2;
TextField t3;
TextField t4onPanel;
Panel p1;
Button b;

public void init() {


add(t1= new TextField(20));
add(t2= new TextField(20));
add(t3= new TextField(20));
t4onPanel = new TextField(20);
p1 = new Panel();
p1.setBackground(new Color(0).yellow);
p1.add(t4onPanel);
add(p1);
add(b = new Button("reset TextFields"));
b.addActionListener(this);
}

public void actionPerformed(ActionEvent ae) {


if (ae.getSource() == b)

Reset all textfields in one shot 34


Real's HowTo PDF version

resetTextFields(this);
}

public static void resetTextFields(Container c) {


Component [] components = c.getComponents();
for (int i = 0; i <components.length; i++ ) {
if (components[i] instanceof Container)
resetTextFields((Container) components[i]) ;
else if (components[i] instanceof TextField)
((TextField) components[i]).setText("") ;
}
}
}

<HTML><HEAD></HEAD><BODY>
<APPLET CODE="FirstApplet.class"
NAME="myApplet"
HEIGHT=200 WIDTH=200>
</APPLET></BODY></HTML>

Limit a TextField to Uppercase


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0279.html

[JDK1.1]
import java.awt.*;
import java.awt.event.*;

public class UpperTF extends Frame {


public static void main(String argv[]) {
new UpperTF().setVisible(true);
}

public UpperTF() {
setLayout(new FlowLayout());
TextField tf = new TextField(10);
add(tf);
tf.addKeyListener(
new KeyAdapter() {
public void keyPressed(KeyEvent e) {
if (Character.isLetter(e.getKeyChar()))
e.setModifiers(Event.SHIFT_MASK);
}
});
pack();

addWindowListener(
new WindowAdapter() {
public void windowClosing(WindowEvent e) {

Limit a TextField to Uppercase 35


Real's HowTo PDF version

System.exit(0);
}
}
);
}

public Dimension getPreferredSize() {


return new Dimension(200,200);
}
}

Have an ImageButton
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0245.html

This implementation of an ImageButton requires JDK1.1 and is a good example of the new Event

architecture. This ImageButton needs 2 GIF images representing the normal and pressed state ( ).
Also a method to disable the button by using a special filter is given.

[ImageButton.java]

import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;
import java.net.*;

public class ImageButton extends Canvas {


protected ActionListener actionListener = null;
int w,h;
boolean clicked;
boolean down;
boolean enabled;
Image UPimage;
Image DOWNimage;
Image disabledimage;

public ImageButton(URL up_b, URL down_b) {


clicked=false;
down=false;
enabled=true;
InitImage(up_b,down_b);
setSize(w,h);
addMouseListener(new ImageButtonMouseListener());
addMouseMotionListener(new ImageButtonMouseMotionListener());
}

public void InitImage(URL up, URL down) {


MediaTracker tracker;

Have an ImageButton 36
Real's HowTo PDF version

try {
UPimage = getToolkit().getImage(up);
DOWNimage = getToolkit().getImage(down);
tracker = new MediaTracker(this);
tracker.addImage(UPimage,0);
tracker.addImage(DOWNimage,1);
tracker.waitForAll();
}
catch (InterruptedException e) {
e.printStackTrace();
}
disabledimage=createImage(new FilteredImageSource
(UPimage.getSource(),new ImageButtonDisableFilter()));
w=UPimage.getWidth(this);
h=UPimage.getHeight(this);
}

public void paint(Graphics g) {


if (down) {
g.drawImage(DOWNimage,0,0,this);
}
else {
if (enabled) {
g.drawImage(UPimage,0,0,this);
}
else {
g.drawImage(disabledimage,0,0,this);
}
}
}

public void setEnabled(boolean b) {


enabled=b;
repaint();
}

public boolean isEnabled() {


return (enabled);
}

public void addActionListener(ActionListener l) {


actionListener =
AWTEventMulticaster.add(actionListener,l);
}
public void removeActionListener(ActionListener l) {
actionListener =
AWTEventMulticaster.remove(actionListener, l);
}

public class ImageButtonMouseListener extends MouseAdapter {


public void mousePressed(MouseEvent e) {
Point p = e.getPoint();
if ((p.x < w)&&(p.y < h)&&(p.x > 0)&&(p.y > 0)&&(enabled==true)) {
clicked=true;

Have an ImageButton 37
Real's HowTo PDF version

down=true;
repaint();
}
}
public void mouseReleased(MouseEvent e) {
Point p = e.getPoint();
if (down) {
down=false;
repaint();
}
if ((p.x < w)&&(p.y < h)&&(p.x > 0)&&(p.y > 0)&&(clicked==true)) {
ActionEvent ae =
new ActionEvent(e.getComponent(),0,"click");
if (actionListener != null) {
actionListener.actionPerformed(ae);
}
}
clicked=false;
}
}
public class ImageButtonMouseMotionListener extends
MouseMotionAdapter {
public void mouseDragged(MouseEvent e) {
Point p = e.getPoint();
if ((p.x < w)&&(p.y < h)&&(p.x > 0)&&(p.y > 0)&&(clicked==true)) {
if (down==false) {
down=true;
repaint();
}
}
else {
if (down==true) {
down=false;
repaint();
}
}
}
}

public Dimension getPreferredSize() {


return (new Dimension(UPimage.getWidth(this),
UPimage.getHeight(this)));
}

public Dimension getMinimumSize() {


return getPreferredSize();
}

class ImageButtonDisableFilter extends RGBImageFilter {


public ImageButtonDisableFilter() {
canFilterIndexColorModel=true;
}
public int filterRGB(int x, int y, int rgb) {
return (rgb & ~0xff000000) | 0x80000000;

Have an ImageButton 38
Real's HowTo PDF version

}
}
}

[TestImageButton.java]

import java.awt.*;
import java.awt.event.*;
import java.applet.*;
import java.net.*;

public class TestImageButton extends Applet


implements ActionListener,ItemListener {
ImageButton ib;
Checkbox c;

public void init() {


setLayout(new FlowLayout());
try {
ib = new ImageButton
(new URL(getCodeBase(), "Gumby.gif"),
new URL(getCodeBase(), "Gumbyblu.gif"));
c = new Checkbox("disable");
ib.addActionListener(this);
c.addItemListener(this);
add(ib);
add(c);
}
catch (Exception e) {
e.printStackTrace();
}
}

public void actionPerformed(ActionEvent e) {


if (e.getSource() == ib) System.out.println("Click ImageButton");
}

public void itemStateChanged(ItemEvent ie) {


ib.setEnabled(!ib.isEnabled());
}
}

Reset a checkbox group


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0221.html

import java.applet.*;
import java.awt.*;

Reset a checkbox group 39


Real's HowTo PDF version

public class radio extends Applet {


CheckboxGroup cbg;
public void init() {
add(new Label("Payment mode?"));
cbg = new CheckboxGroup();
add(new Checkbox("Visa", cbg, false));
add(new Checkbox("Mastercard", cbg, false));
add(new Checkbox("American Express", cbg, false));
add(new Checkbox("Cash", cbg, true));
add(new Button("clear radio"));
}

public boolean action(Event e, Object o) {


if (o.equals("clear radio")){
Checkbox current = cbg.getCurrent();
cbg.setCurrent( null );
current.setState( false );
return true;
}
return false;
}
}

Set the listbox width


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0231.html

The width can be specified via the preferredSize method. This class lets you specify a font (fixed pitch) and
calculate the appropriate width in pixels.

class myListbox extends List {


int width;
int height;
public myListbox(int r, int n, boolean m){
// (r) line number, (n) width, (m) multiselect
this(r, n, m, new Font("Courier", Font.BOLD, 10));
width = n;
height = r;
}

public myListbox(int r, int n, boolean m, Font f){


super(r,m);
width = n;
height = r;
setFont(f);
}

public Dimension preferredSize (){


FontMetrics fm=getFontMetrics(getFont());

Set the listbox width 40


Real's HowTo PDF version

// the character W used as reference


return new Dimension
(fm.charWidth('W')*width, fm.getHeight()*height);
}
}

Align the column in a List


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0244.html

The trick is to use a FIXED width character set like "Courier".

ml = new List();
my.setFont(new Font("Courier", Font.BOLD, 10));

When inserting a line, we simply pad spaces as needed. Here the first column is 20 characters wide, the
second 10 and the last one the remaining.

insertItem(ml, "ARCHIVE", "STATUS", "PORT");

public void insertItem(List lbx,


String col1, String col2, String col3) {
String spaces2 = " ";
String spaces10 = " ";
String spaces20 = spaces10 + spaces10;
lbx.addItem(col1 +
spaces20.substring(0,20-col1.length()) +
spaces2 +
col2 +
spaces10.substring(0,10-col2.length()) +
col3);
}

In real life, the preferred way would be to extend the java.awt.List and override the addItem method.

Have a srolling text display using a List


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0271.html

A srolling text display can be used to log informations or events. In this snippet, we are using a List
component to display the data. We are keeping only the last 10 events. It's a good idea to limit the amount of
data kept in the List , in fact we have no choice because the maximum capacity is about 32k (Win).

Align the column in a List 41


Real's HowTo PDF version

import java.awt.*;
import java.awt.event.*;

public class TelnetLikeDisplay extends Applet


implements ActionListener {
Button b;
int i = 0;
static final int LINE_BUFFERED = 10;
static final int LINE_DISPLAYED = LINE_BUFFERED - 1;
List l;

public void init() {


setLayout(new FlowLayout(FlowLayout.LEFT));
add(b = new Button("New Line"));
b.addActionListener(this);
add(l = new List(5));
l.setSize(100,100);
l.setForeground(new Color(0).yellow);
l.setBackground(new Color(0).black);
}

public void actionPerformed(ActionEvent ae) {


String newLine = "Line #" + i;
if (i <LINE_BUFFERED) {
l.addItem(newLine);
l.makeVisible(i);
}
else {
l.remove(0);
l.add(newLine, LINE_DISPLAYED);
l.makeVisible(LINE_DISPLAYED);
}
i++;
}
}

Label dynamic resizing


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0232.html

If there is no Layout Manager installed, try something like this:

aLabel.setText ("A very long label");


aLabel.resize (aLabel.preferredSize());

With a Layout Manager, you have to validate() the layout to redraw the components invalidated.

Label aLabel = new Label("short label");


aLabel.setText ("A very long label");

Have a srolling text display using a List 42


Real's HowTo PDF version

this.validate();

While this method works in Netscape or the Appletviewer, on IE4/5 there is no resizing. You may want to try
this instead (thanks to Dan for the tip):

Label aLabel = new Label("short label");


aLabel.setText(""A very long label");
aLabel.invalidate(); // make sure the component is marked as non-valid
this.validate();

This example how to change a Label or a String drawn with the drawString method by clicking on a button.

import java.awt.*;
import java.awt.event.*;
import java.applet.*;

public class TestPaint extends Applet


implements ActionListener {
MyPanel p;
Label l;
Button b1, b2;
TextField t1, t2;

public void init() {


setLayout(new FlowLayout());
t1 = new TextField(10);
b1 = new Button("Change Label");
add(t1); add(b1);
t2 = new TextField(10);
b2 = new Button("Change drawString");
add(t2); add(b2);
l = new Label("label text");
add(l);

// a Panel with a drawString call


p = new MyPanel();
add(p);
b1.addActionListener(this);
b2.addActionListener(this);
}

public void actionPerformed(ActionEvent e) {


if (e.getSource() == b1) {
l.setText(t1.getText());
l.invalidate();
validate();
}
if (e.getSource() == b2) {
p.someString = t2.getText();
p.repaint();
}
}
}

Label dynamic resizing 43


Real's HowTo PDF version

class MyPanel extends Panel {


String someString = "drawstring";

MyPanel() { super(); }

public void paint (Graphics g) {


g.drawString(someString, 10,50);
}

public Dimension getPreferredSize() {


return new Dimension (100,100);
}
}

Make a TextArea "word-wrap"


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0241.html

Simply create the TextArea with no horizontal scrollbar.

myTextArea = new TextArea


("text", 3 , 100 , TextArea.SCROLLBARS_VERTICAL_ONLY);

Synchronize a TextArea versus a Choice


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0281.html

import java.awt.*;
import java.awt.event.*;

class ChoiceEx extends Frame implements ItemListener {


Choice choice = new Choice();
TextArea textarea = new TextArea();
ChoiceEx() {
super("");

for (int i=0; i<10; i++) {


choice.addItem("item "+i);
}
// Set listeners
choice.addItemListener(this);
add(choice, BorderLayout.SOUTH);
add(textarea, BorderLayout.NORTH);
pack();

Make a TextArea "word-wrap" 44


Real's HowTo PDF version

setVisible(true);
}

// When list or choice is updated


public void itemStateChanged(ItemEvent evt) {
textarea.setText("Item #" + choice.getSelectedIndex());
}

static public void main(String[] args) {


new ChoiceEx();
}
}

Display underlined text


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0258.html

import java.applet.*;
import java.awt.*;

public class underlineText extends Applet{


String s = "Underlined text";
int x=10;
int y=10;

public void init() {}

public void paint(Graphics g) {


g.drawString(s, x,y);
g.drawLine(x , y+2 , x+getFontMetrics(getFont()).stringWidth(s) , y+2 );
}
}

Check this How-to for underlined text with a Label component.


Check this How-to for underlined text in Swing.

Display vertical text


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0259.html

import java.applet.*;
import java.awt.*;

public class verticalText extends Applet {

Synchronize a TextArea versus a Choice 45


Real's HowTo PDF version

String s = "Vertical text";


int x=10;
int y=10;
int v;
public void init() {}

public void paint(Graphics g) {


v=g.getFontMetrics(getFont()).getHeight()+1;
System.out.println(v);
int j =0;
int k= s.length();
while(j < k+1) {
if (j == k)
g.drawString(s.substring(j),x, y+(j*v));
else
g.drawString(s.substring(j,j+1),x, y+(j*v));
j++;
}
}
}

[JDK1.4]

import java.awt.geom.AffineTransform;
import java.awt.Graphics2D;

public void paint(Graphics g){


Graphics2D g2d = (Graphics2D)g;

// clockwise 90 degrees
AffineTransform at = new AffineTransform();
// thanks to M.C. Henle for the bug fix!
at.setToRotation(-Math.PI/2.0, width/2.0, height/2.0);
g2d.setTransform(at);
g2d.drawString("Vertical text", x, y);
}

Have Label with many lines


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0269.html

The Label component included in the AWT do not support "\n" in its definition. The following class
implements a multi-line Label. Lines are separated byt the token "\n". Lines can be left, right or center
justified. Plus, there is a possibility to have a border around the label.

import java.awt.*;
import java.util.*;

Display vertical text 46


Real's HowTo PDF version

public class MultiLineLabel extends Canvas {


public static final int LEFT = 0;
public static final int CENTER = 1;
public static final int RIGHT = 2;
private String text;
private String lines[];
private int num_lines;
private int line_height;
private int line_ascent;
private int line_widths[];
private int max_width;
private int alignment;
private boolean border;
private int topBottomMargin;
private int leftRightMargin;
private int x = 0;
private int y = 0;
Dimension offDimension;
Image offImage;
Graphics offGraphics;
Color borderColor = new Color(0).black;

public MultiLineLabel(String s, int i, boolean b) {


// s the label
// i alignement MultiLineLabel.CENTER, MultiLineLabel.RIGHT,
// MultiLineLabel.LEFT
// default MultiLineLabel.LEFT
// b border present or not
setAlignment(i);
setText(s);
setBorder(b);
}

public MultiLineLabel(String string, int i) {


this(string, i, false);
}

public MultiLineLabel(String string) {


this(string, 0);
}

public MultiLineLabel() {
this("", 0);
}

public void addNotify() {


super.addNotify();
calc();
}

public void setX(int i) { x = i; }


public void setY(int i) { y = i; }

Have Label with many lines 47


Real's HowTo PDF version

public int getLeftRightMargin() {


return leftRightMargin;
}

public void setLeftRightMargin(int i) {


// make sense only if alignment is MultiLineLabel.LEFT!
if (i >= 0) leftRightMargin = i ;
}

public int getAlignment() {


return alignment;
}

public void setAlignment(int i) {


switch (alignment) {
case 0:
case 1:
case 2:
alignment = i;
break;
default:
throw new IllegalArgumentException();
}
repaint();
}

public int getTopBottomMargin() {


return topBottomMargin;
}

public void setTopBottomMargin(int i) {


if (i >= 0) topBottomMargin = i;
}

public void setFont(Font font) {


super.setFont(font);
calc();
repaint();
}

public Dimension getMinimumSize() {


Dimension d = new Dimension
(max_width + leftRightMargin * 2,
num_lines * line_height + topBottomMargin * 2);
if (d.width == 0) d.width = 10;
if (d.height == 0) d.height = 10;
return d;
}

public Dimension getPreferredSize() {


return getMinimumSize();
}

Have Label with many lines 48


Real's HowTo PDF version

public boolean getBorder() {


return border;
}

public void setBorder(boolean flag) {


border = flag;
}

public void setText(String s) {


// parse the string , "\n" is a the line separator
StringTokenizer st =
new StringTokenizer(s,"\n");
num_lines = st.countTokens();
lines = new String[num_lines];
line_widths = new int[num_lines];
for (int i = 0; i < num_lines; i++)
lines[i] = st.nextToken();
calc();
repaint();
text = new String(s);
}

public String getText() {


return text;
}

public Color getBorderColor() {


return borderColor;
}

public void setBorderColor(Color c) {


borderColor = c;
}

private void calc() {


// calc dimension and extract maximum width
Font f = getFont();
if (f != null) {
FontMetrics fm = getFontMetrics(f);
if (fm != null) {
line_height = fm.getHeight();
line_ascent = fm.getAscent();
max_width = 0;
for (int i = 0; i < num_lines; i++) {
line_widths[i] =
fm.stringWidth(lines[i]);
if (line_widths[i] > max_width)
max_width = line_widths[i];
}
}
}
}

public void update(Graphics g) {

Have Label with many lines 49


Real's HowTo PDF version

super.paint(g);
Dimension d = getSize();
if ( (offGraphics == null) ||
(d.width != offDimension.width) ||
(d.height != offDimension.height)
) {
offDimension = d;
offImage = createImage(d.width, d.height);
offGraphics = offImage.getGraphics();
}
offGraphics.setColor(getBackground());
offGraphics.fillRect
(x, y, getSize().width - 1,
getSize().height - 1);
if (border) {
offGraphics.setColor(borderColor);
offGraphics.drawRect
(x, y, getSize().width - 1, getSize().height - 1);
}
int j = line_ascent +
(d.height - num_lines * line_height) / 2;
for (int k = 0; k < num_lines; ) {
int i;
switch (alignment) {
case 0:
i = 0;
break;
case 2:
i = d.width - line_widths[k];
break;
default:
i = (d.width - line_widths[k]) / 2;
break;
}
i += leftRightMargin;
offGraphics.setColor(getForeground());
offGraphics.drawString(lines[k], i + x, j + y);
k++;
j += line_height;
}
g.drawImage(offImage,0,0,this);
}

public void paint(Graphics g) {


update(g);
}

public static void main(String args[]){


Frame f = new Frame("Test MultiLineLabel");
f.setSize(200,200);
f.setLayout(new FlowLayout());
f.setVisible(true);

MultiLineLabel mll1 = new MultiLineLabel

Have Label with many lines 50


Real's HowTo PDF version

("This a test!\nsecond line\nthird line",


MultiLineLabel.LEFT, true);
// mll1.setBorderColor(new Color(0).blue);
mll1.setLeftRightMargin(15);
mll1.setTopBottomMargin(15);
f.add(mll1);

Button b = new Button("Dummy");


f.add(b);

MultiLineLabel mll2 = new MultiLineLabel


("123\n4\n567", MultiLineLabel.RIGHT, false);
mll2.setForeground(new Color(0).yellow);
mll2.setBackground(new Color(0).black);
f.add(mll2);

f.validate();
}
}

Have a Label with underlined text


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0272.html

[UnderlinedLabel.java]

import java.awt.*;

public class UnderlinedLabel extends Label {


public UnderlinedLabel(){
this("");
}

public UnderlinedLabel(String text){


super(text);
}

public void paint(Graphics g) {


Rectangle r;
super.paint(g);
r = g.getClipBounds();
g.drawLine
(0,
r.height - this.getFontMetrics(this.getFont()).getDescent(),
this.getFontMetrics(this.getFont()).stringWidth(this.getText()),
r.height - this.getFontMetrics(this.getFont()).getDescent());
}
}

[TestUnderlinedLabel.java]

Have a Label with underlined text 51


Real's HowTo PDF version

import java.applet.*;
import java.awt.*;

public class TestUnderlinedLabel extends Applet {


public void init() {
UnderlinedLabel ul1 =
new UnderlinedLabel
("Java How-to");
add(ul1);
}
}

[testapplet.html]

<HTML><HEAD></HEAD><BODY>
<APPLET CODE="TestUnderlinedLabel.class"
NAME="myApplet"
HEIGHT=200 WIDTH=200>
&LT;/APPLET&GT;&LT;/BODY&GT;&LT;/HTML&GT;

Check this How-to for underlined text in Swing.

Have a Label acting as HTML HREF (URLLabel)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0273.html

[URLLabel.java]

import java.applet.*;
import java.awt.*;
import java.awt.event.*;
import java.net.*;

public class URLLabel extends Label {


private java.applet.Applet applet;
private URL url;
private String target = "";
private Color unvisitedURL = Color.blue;
private Color visitedURL = Color.green;

public URLLabel(Applet applet , String url, String text){


this(applet, url, text, "_self");
}

public URLLabel
(Applet applet , String url, String text, String target){
super(text);
setForeground(unvisitedURL);
try {

Have a Label acting as HTML HREF (URLLabel) 52


Real's HowTo PDF version

this.applet = applet;
this.url = new URL(url);
this.target = target;
addMouseListener( new Clicked() );
}
catch (Exception e) {
e.printStackTrace();
}
}

public void paint(Graphics g) {


Rectangle r;
super.paint(g);
r = g.getClipBounds();
g.drawLine(0,
r.height - this.getFontMetrics(this.getFont()).getDescent(),
this.getFontMetrics(this.getFont()).stringWidth(this.getText()),
r.height - this.getFontMetrics(this.getFont()).getDescent());
}

public void setUnvisitedURLColor(Color c) {


unvisitedURL = c;
}

public void setVisitedURLColor(Color c) {


visitedURL = c;
}

class Clicked extends MouseAdapter{


public void mouseClicked(MouseEvent me){
setForeground(visitedURL);
applet.getAppletContext().showDocument(url, target);
}
}
}

[TestURLLabel.java]

import java.applet.*;
import java.awt.*;

public class TestURLLabel extends Applet {


public void init() {
URLLabel ull1 = new URLLabel(this,
"http://www.rgagnon.com/howto.html",
"Java How-to");
add(ull1);
URLLabel ull2 = new URLLabel(this,
"http://www.rgagnon.com/bigindex.html",
"Java How-to BigIndex");
add(ull2);
URLLabel ull3 = new URLLabel(this,
"http://www.rgagnon.com/javadetails/java-0001.html",
"Java How-to 0001");

Have a Label acting as HTML HREF (URLLabel) 53


Real's HowTo PDF version

add(ull3);
URLLabel ull4 = new URLLabel(this,
"http://www.rgagnon.com/javadetails/java-0002.html",
"Java How-to 0002");
add(ull4);
validate();
}
}

[testapplet.html]

<HTML><HEAD></HEAD><BODY>
<APPLET CODE="TestURLLabel.class"
NAME="myApplet"
HEIGHT=200 WIDTH=200>
</APPLET></BODY></HTML>

Try it here.

Display a GIF in a Canvas


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0229.html

import java.awt.*;
import java.awt.image.*;

public class ImageCanvas extends Canvas {


Image image;

public ImageCanvas(String name) {


MediaTracker media = new MediaTracker(this);
image = Toolkit.getDefaultToolkit().getImage(name);
media.addImage(image, 0);
try {
media.waitForID(0);
}
catch (Exception e) {}
}

public ImageCanvas(ImageProducer imageProducer) {


image = createImage(imageProducer);
}

public void paint(Graphics g) {


g.drawImage(image, 0,0, this);
}

public static void main(String argv[]) {

Display a GIF in a Canvas 54


Real's HowTo PDF version

if (argv.length <1) {
System.out.println
("usage: ImageCanvas.class [image file name]");
System.exit(0);
}
Frame frame = new Frame(argv[0]);
frame.setLayout(new BorderLayout());
frame.add("Center", new ImageCanvas(argv[0]));
frame.resize(400,400);
frame.show();
}
}

Embed an image into a Frame


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0302.html

A given image is tiled as the frame background.

The result is not too good with Label...

import java.awt.*;
import java.awt.event.*;

public class ImageFrame extends Frame {

private Image image;

ImageFrame() {
super("");
try {
MediaTracker mt = new MediaTracker (this);
// for Applet, change the method to retrieve the image
// and of course use your own image!
image = Toolkit.getDefaultToolkit().getImage("images/jht.gif");
mt.addImage(image, 0);
mt.waitForID(0);
}
catch (Exception e) {
e.printStackTrace();
}

setLayout(new FlowLayout());

add(new TextField(10));
add(new Button("hello"));
add(new List(20));
add(new TextArea(20,20));
// Label may not look too good ...
add(new Label("Hello"));

Embed an image into a Frame 55


Real's HowTo PDF version

setSize(500, 500);

addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
// change this for an Applet
System.out.println("Bye.");
System.exit(0);
}
}
);
}

public void update( Graphics g) {


paint(g);
}

public void paint(Graphics g) {


if(image != null) {
int x = 0, y = 0;
while(y < getSize().height) {
x = 0;
while(x< getSize().width) {
g.drawImage(image, x, y, this);
x= x + image.getWidth(null);
}
y = y + image.getHeight(null);
}
}
else {
g.clearRect(0, 0, getSize().width, getSize().height);
}
}

static public void main(String[] args) {


ImageFrame iframe = new ImageFrame();
iframe.setVisible(true);
}
}

The result :

Embed an image into a Frame 56


Real's HowTo PDF version

Load several images from a single GIF


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0239.html

It's a good idea to combine small GIFs into a single big one to speed up the loading process. In the following
snippet, I assume that all images are the same height and width. You may want to get this GIF ( ) if you
want to try the example on your workstation!

import java.applet.*;
import java.awt.*;
import java.io.*;
import java.net.*;

public class strip extends Applet{


int iconHeight = 16;
int iconWidth = 16;
int iconCount = 2;
Image icon[] = new Image[iconCount];
Image allIcons;

public void init(){


loadImages("item.gif");
}

Load several images from a single GIF 57


Real's HowTo PDF version

public void paint(Graphics g) {


g.drawImage(allIcons, 0, 0, this);
g.drawImage(icon[0], 0, 20, this);
g.drawImage(icon[1], 0, 40, this);
}

public void loadImages(String s) {


MediaTracker t=new MediaTracker(this);
allIcons=createImage(1,1);
try {
URL u=new URL(getCodeBase(), s);
allIcons=Toolkit.getDefaultToolkit().getImage(u);
t.addImage(allIcons,0);
}
catch (MalformedURLException me) {
System.out.println("MalformedURLException: " + me);
}
try {
t.waitForAll(15000);
}
catch (InterruptedException e) {
System.out.println("interrupted");
}
for (int i=0; i < iconCount; i++) {
Image z=createImage(iconWidth,iconHeight);
Graphics g=z.getGraphics();
g.clipRect(0,0,iconWidth,iconHeight);
g.drawImage(allIcons,-i*iconWidth,0,this);
icon[i]=z;
}
}
}

Load an Image from a JAR file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0240.html

[JDK1.1 application]

String imgName = "image.jpg";


URL imgURL = getClass().getResource(imgName);
Toolkit tk = Toolkit.getDefaultToolkit();
Image img = null;
try {
MediaTracker m = new MediaTracker(this);
img = tk.getImage(imgURL);
m.addImage(img, 0);
m.waitForAll();
}

Load an Image from a JAR file 58


Real's HowTo PDF version

catch (Exception e) {
e.printStackTrace();
}

[JDK 1.1 applet]


Because of some security reason, it's not possible with some browser (like Netscape) to use the getResource()
method from an Applet. Instead we must use the getResourceAsStream method.

Image img = null;

try {
MediaTracker m = new MediaTracker(this);
InputStream is = getClass().getResourceAsStream("image.gif");
//
// if your image is in a subdir in the jar then
// InputStream is = getClass().getResourceAsStream("img/image.gif");
// for example
//
BufferedInputStream bis = new BufferedInputStream(is);
// a buffer large enough for our image
//
// can be
// byte[] byBuf = = new byte[is.available()];
// is.read(byBuf); or something like that...
byte[] byBuf = = new byte[10000];

int byteRead = bis.read(byBuf,0,10000);


img = Toolkit.getDefaultToolkit().createImage(byBuf);
m.addImage(img, 0);
m.waitForAll();
}
}
catch(Exception e) {
e.printStackTrace();
}

[JDK 1.2 application]

URL url = this.getClass().getResource("myIcon.gif");


button.setIcon(new ImageIcon(url));

Load an Image from a JAR file (again)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0436.html

public static ImageIcon getImageIcon(String name) {


return new ImageIcon(ClassLoader.getSystemResource(name));
}

Load an Image from a JAR file (again) 59


Real's HowTo PDF version

ImageIcon img = getImageIcon("resources/images/icone.gif");

Remember that it is always possible to the Java built-in icons so that you don't have to include your own
standard icons.

public static Icon getIconForType(int iconType) {


switch (iconType) {
case 0:
return UIManager.getIcon("OptionPane.errorIcon");
case 1:
return UIManager.getIcon("OptionPane.informationIcon");
case 2:
return UIManager.getIcon("OptionPane.warningIcon");
case 3:
return UIManager.getIcon("OptionPane.questionIcon");
}
return null;
}

A list of what icons are available can be found here

Scale an Image
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0243.html

import java.awt.image.*;
import java.awt.*;
import java.net.*;

public class app extends java.applet.Applet {


Image source;
Image resizedImage;

public void init() {


MediaTracker media = new MediaTracker(this);
// java how-to image for example, can be JPG
source = getImage(getDocumentBase(),"../images/jht.gif");
media.addImage(source,0);
try {
media.waitForID(0);
// scale down, half the original size
ImageFilter replicate =
new ReplicateScaleFilter
(source.getWidth(this)/2, source.getHeight(this)/2);
ImageProducer prod =
new FilteredImageSource(source.getSource(),replicate);

Scale an Image 60
Real's HowTo PDF version

resizedImage = createImage(prod);
media.addImage(resizedImage,1);
media.waitForID(1);
}
catch(InterruptedException e) {}
}

public void paint(Graphics g) {


g.drawImage(source, 10,10,this);
g.drawImage(resizedImage,10, 80,this);
}
}

Try it here.

Modern JDK has now a complete library devoted to graphic manipulation.

The following exampe takes a JPG file as input , rescale it to the passed parameters and writes the result in the
specified output file.

import java.awt.*;
import java.awt.geom.*;
import java.awt.image.*;
import java.io.*;
import javax.imageio.*;

public class ScaleJPG {


public static void scale(String src, int width, int height, String dest)
throws IOException {
BufferedImage bsrc = ImageIO.read(new File(src));
BufferedImage bdest =
new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics2D g = bdest.createGraphics();
AffineTransform at =
AffineTransform.getScaleInstance((double)width/bsrc.getWidth(),
(double)height/bsrc.getHeight());
g.drawRenderedImage(bsrc,at);
ImageIO.write(bdest,"JPG",new File(dest));
}

public static void main(String[] args) {


if (args.length == 4) {
try {
ScaleJPG.scale
(args[0],Integer.parseInt(args[1]),
Integer.parseInt(args[2]), args[3]);
}
catch (Exception e) {
e.printStackTrace();
}
}
else {
System.out.println("\nUsage: java ScaleJPG src width height dest\n");

Scale an Image 61
Real's HowTo PDF version

}
}
}

Example :

>java ScaleJPG javahowto.jpg 250 70 javahowto2.jpg

Input:

Ouput:

Fade an image
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0249.html

This example display a GIF with a fade-in, fade-out effect.

import java.applet.*;
import java.awt.*;
import java.awt.image.*;
import java.net.*;

public class FadeImage extends Applet {


Image img, faded;
int level, sign;
MediaTracker tracker;
AlphaFilter f;
FilteredImageSource fis;

public void init() {


level = 0;
sign = 15;
tracker = new MediaTracker(this);
try {
img = getImage(new URL(getDocumentBase(), "../images/gumby.gif"));
tracker.addImage(img,0);
tracker.waitForID(0);
}
catch (Exception e) {
e.printStackTrace();
}
f = new AlphaFilter();

Fade an image 62
Real's HowTo PDF version

f.setLevel(level);
fis = new FilteredImageSource(img.getSource(), f) ;

FadeThread ft = new FadeThread();


ft.delayedFading(this, 20);
ft.start();
}

public void paint(Graphics g) {


if (faded != null) {
g.drawImage(faded,0,0,this);
}
}

public void fadeIt() {


Graphics g = this.getGraphics();
level += sign;
if (level < 0) {
level=0;
sign = sign * -1;
}
if (level > 255) {
level=255;
sign = sign * -1;
try {
Thread.sleep(1000);
}
catch (Exception e) {}
}
f.setLevel(level);
if (faded != null) faded.flush();
faded = this.createImage(fis);
tracker.addImage(faded,0);
try {
tracker.waitForID(0);
}
catch (Exception ex) {
ex.printStackTrace();
}
repaint();
}

class FadeThread extends Thread {


FadeImage fadeApplet;
int delay;

public void delayedFading(FadeImage f, int delay) {


this.fadeApplet = f;
this.delay = delay;
}

public void run() {


while (true) {
try {

Fade an image 63
Real's HowTo PDF version

sleep(delay);
fadeApplet.fadeIt();
}
catch (Exception e) {
e.printStackTrace();
}
}
}
}

class AlphaFilter extends RGBImageFilter {


private int level;

public AlphaFilter() {
canFilterIndexColorModel = true;
}

public void setLevel(int lev) {


level = lev;
}

public int filterRGB(int x, int y, int rgb) {


int a = level * 0x01000000;
return (rgb & 0x00ffffff) | a;
}
}
}

Try it here.

Rotate an image
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0248.html

The following snippet rotates an image (90 degrees). The applet assumes the dimension 32x32 for the image.

You may want to grap this image for testing purpose.

import java.applet.Applet;
import java.awt.*;
import java.awt.image.*;
import java.net.*;

public class RotateGumby extends Applet {


Image img = null;
Image rot = null;

int buffer[] = new int[32 * 32];


int rotate[] = new int[32 * 32];

Rotate an image 64
Real's HowTo PDF version

public void init() {


try {
MediaTracker tracker = new MediaTracker (this);
img = getImage(new URL(getDocumentBase(), "gumby.gif"));
tracker.addImage (img, 0);
tracker.waitForAll();
PixelGrabber grabber =
new PixelGrabber(img, 0, 0, 32, 32, buffer, 0, 32);
try {
grabber.grabPixels();
}
catch(InterruptedException e) {
e.printStackTrace();
}
for(int y = 0; y < 32; y++) {
for(int x = 0; x < 32; x++) {
rotate[((32-x-1)*32)+y] = buffer[(y*32)+x];
}
}
rot = createImage(new MemoryImageSource(32, 32, rotate, 0, 32));
}
catch (Exception e) {
e.printStackTrace();
}
}

public void update( Graphics g) {


paint(g);
}

public void paint(Graphics g) {


g.drawImage(img, 0, 0,this);
g.drawImage(rot,0, 40, this);
}
}

The next example will rotate a picture 5 degrees at a time. We are using the Java2D package (and Swing).

import java.awt.*;
import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;

public class RotatePanel extends JPanel {


private Image image;
private double currentAngle;

public RotatePanel(Image image) {


this.image = image;
MediaTracker mt = new MediaTracker(this);
mt.addImage(image, 0);
try {
mt.waitForID(0);

Rotate an image 65
Real's HowTo PDF version

}
catch (Exception e) {
e.printStackTrace();
}
}

public void rotate() {


//rotate 5 degrees at a time
currentAngle+=5.0;
if (currentAngle >= 360.0) {
currentAngle = 0;
}
repaint();
}
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
AffineTransform origXform = g2d.getTransform();
AffineTransform newXform = (AffineTransform)(origXform.clone());
//center of rotation is center of the panel
int xRot = this.getWidth()/2;
int yRot = this.getHeight()/2;
newXform.rotate(Math.toRadians(currentAngle), xRot, yRot);
g2d.setTransform(newXform);
//draw image centered in panel
int x = (getWidth() - image.getWidth(this))/2;
int y = (getHeight() - image.getHeight(this))/2;
g2d.drawImage(image, x, y, this);
g2d.setTransform(origXform);
}

public Dimension getPreferredSize() {


return new Dimension (image.getWidth(this), image.getHeight(this));
}

public static void main(String[] args) {


JFrame f = new JFrame();
Container cp = f.getContentPane();
cp.setLayout(new BorderLayout());
Image testImage =
Toolkit.getDefaultToolkit().getImage("c:/temp/gumby.gif");
final RotatePanel rotatePanel = new RotatePanel(testImage);
JButton b = new JButton ("Rotate");
b.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent ae) {
rotatePanel.rotate();
}
});
cp.add(rotatePanel, BorderLayout.CENTER);
cp.add(b, BorderLayout.SOUTH);
f.pack();
f.setVisible(true);
}

Rotate an image 66
Real's HowTo PDF version

Create a scrollable canvas


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0230.html

JDK1.1 using a ScrollPane

import java.applet.*;
import java.awt.*;

public class apptest extends Applet {


Canvas c;
ScrollPane s;

public void init() {


setLayout(new BorderLayout());
s = new ScrollPane();
s.setSize(100,100);
add("Center", s);
c = new myCanvas();
c.setSize(500,300);
s.add(c);
}

class myCanvas extends Canvas {


Image buffImage;
Graphics offscreen;
boolean initDone = false;

myCanvas() { super(); }
public void paint(Graphics g) {
if (!initDone)
initpaint(g);
else
g.drawImage(buffImage, 0, 0, this);
}

public void update(Graphics g) {


g.drawImage(buffImage, 0, 0, this);
}

public void initpaint(Graphics g) {


try {
buffImage = this.createImage(500, 500);
offscreen = buffImage.getGraphics();
offscreen.setColor(Color.black);
offscreen.fillRect(0, 0, 500, 500);
offscreen.setColor(Color.white);
offscreen.setFont(new Font("Courier", Font.ITALIC, 42));

Create a scrollable canvas 67


Real's HowTo PDF version

offscreen.drawString("Hello World!", 0, 50);


initDone = true;
g.drawImage(buffImage,0,0, this);
}
catch (Exception e) {
e.printStackTrace();
}
}
}
}

JDK1.0.2 using a Canvas with Scrollbar

import java.applet.*;
import java.awt.*;

public class apptest extends Applet {


ScrollCanvas sc;
public void init() {
setLayout(new FlowLayout());
sc = new ScrollCanvas
(150,150, 300,200, Color.black,
Color.white);
add(sc);
}

public boolean handleEvent(Event e) {


if (e.target instanceof Scrollbar) {
switch (e.id) {
case Event.SCROLL_ABSOLUTE:
case Event.SCROLL_PAGE_DOWN:
case Event.SCROLL_PAGE_UP:
case Event.SCROLL_LINE_UP:
case Event.SCROLL_LINE_DOWN:
sc.redraw();
return true;
}
}
return super.handleEvent(e);
}
}

class ScrollCanvas extends Panel {


int vw,vh;
int rw,rh;
Color b,f;
myCanvas c;
Scrollbar sv, sh;

// constructor
// visible h w
// real h w
// background foreground
ScrollCanvas

Create a scrollable canvas 68


Real's HowTo PDF version

(int vw1, int vh1, int rw1, int rh1, Color b1, Color f1) {
super();
vw = vw1; vh = vh1;
rh = rh1; rw = rw1;
b = b1; f = f1;
int ScrollIncrement = 10;
setLayout(new BorderLayout());
c = new myCanvas(vw, vh, rw, rh, b ,f);
add("West", c);
sv = new Scrollbar
(Scrollbar.VERTICAL,0, ScrollIncrement, 0, rh);
add("East", sv);
sh = new Scrollbar
(Scrollbar.HORIZONTAL, 0, ScrollIncrement, 0, rw);
add("South", sh);
}

public void redraw() {


int y = sv.getValue();
int x = sh.getValue();
c.draw(x,y);
}

public Dimension minimumSize() {


return new Dimension(vw,vh);
}

public Dimension preferredSize() {


return new Dimension(vw,vh);
}
}

class myCanvas extends Canvas {


int vw, vh;
int rw, rh;
Color b, f;
int x, y;
Image buffImage;
Graphics offscreen;
boolean initDone;

myCanvas
(int vw1, int vh1, int rw1, int rh1, Color b1, Color f1) {
super();
vw = vw1; vh = vh1;
rh = rh1; rw = rw1;
b = b1; f = f1;
initDone = false;
repaint();
}

public void paint(Graphics g) {


if (!initDone)
initpaint(g);

Create a scrollable canvas 69


Real's HowTo PDF version

else
g.drawImage(buffImage, x, y, this);
}

public void update(Graphics g) {


g.drawImage(buffImage, x, y, this);
}

public void initpaint(Graphics g) {


try {
buffImage = this.createImage(rw, rh);
offscreen = buffImage.getGraphics();
offscreen.setColor(b);
offscreen.fillRect(0, 0, rw, rh);
offscreen.setColor(f);
offscreen.setFont(new Font("Courier", Font.ITALIC, 42));
offscreen.drawString("Hello World!", 0, 50);
initDone = true;
g.drawImage(buffImage,0,0, this);
}
catch (Exception e) {
System.out.println("oups...");
}
}

public void draw (int x1, int y1) {


x = -x1;
y = -y1;
update(getGraphics());
}

public Dimension minimumSize() {


return new Dimension(vw,vh);
}

public Dimension preferredSize() {


return new Dimension(vw,vh);
}
}

Use an Image as the Applet background


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0233.html

import java.applet.Applet;
import java.net.*;

// TILE BACKGROUND
// in the HTML use :

Use an Image as the Applet background 70


Real's HowTo PDF version

// PARAM NAME="bgImage" VALUE="images/myImage.jpg"


// in the APPLET tag

public class Tile extends Applet {


Image bgImage = null;

public void init() {


try {
MediaTracker tracker = new MediaTracker (this);
bgImage = getImage
(new URL(getCodeBase(), getParameter("bgImage")));
tracker.addImage (bgImage, 0);
tracker.waitForAll();
}
catch (Exception e) {
e.printStackTrace();
}
setLayout(new FlowLayout());
add(new Button("Ok"));
add(new TextField(10));
}

public void update( Graphics g) {


paint(g);
}

public void paint(Graphics g) {


if(bgImage != null) {
int x = 0, y = 0;
while(y < size().height) {
x = 0;
while(x<size().width) {
g.drawImage(bgImage, x, y, this);
x=x+bgImage.getWidth(null);
}
y=y+bgImage.getHeight(null);
}
}
else {
g.clearRect(0, 0, size().width, size().height);
}
}
}

<HTML>
<TABLE><TR><TD>
<APPLET CODE=Tile.class WIDTH=150 HEIGHT=150>
<PARAM NAME="bgImage" VALUE="images/jht.gif">
</APPLET>
&LT;/HMTL&GT;

Try it here.

Use an Image as the Applet background 71


Real's HowTo PDF version

Have a simple Image browser


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0277.html

[imagelist.txt]

jht.gif|JAVA How-to
jsht.gif|Javascript How-to
pht.gif|Powerbuilder How-to

[application version]

import java.awt.*;
import java.awt.event.*;
import java.net.*;
import java.io.*;

public class ImageBrowser {


public static void main(String s[]) {
AFrame f = new AFrame();
}
}

class AFrame extends Frame implements ActionListener {


List lbx;
MyCanvas can;
String url[] = new String[50];

public AFrame() {
setTitle("Image selection, double click to display");
setLayout(new GridLayout(1,2));
setSize(800,600);
lbx = new List();
can = new MyCanvas();
add(lbx); add(can);
initLbx();
// action on listbox double click
lbx.addActionListener(this);
// to close the Frame
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
setVisible(true);
}

public void actionPerformed (ActionEvent ae) {

Have a simple Image browser 72


Real's HowTo PDF version

String theUrl = url[lbx.getSelectedIndex()];


MediaTracker media = new MediaTracker(this);
Image image =
Toolkit.getDefaultToolkit().getImage(theUrl);
media.addImage(image, 0);
try {
media.waitForID(0);
can.setImage(image);
}
catch (Exception e) { e.printStacktrace();}
}

public void initLbx() {


int i = 0;
try {
String aLine = "";
BufferedReader in
= new BufferedReader(new FileReader("imagelist.txt"));
while(null != (aLine = in.readLine())) {
java.util.StringTokenizer st =
new java.util.StringTokenizer(aLine, "|");
url[i++] = st.nextToken();
// lbx.addItem(st.nextToken());
lbx.add(st.nextToken());
}
}
catch(Exception e) { e.printStackTrace();}
}
}

class MyCanvas extends Canvas {


private Image image;
public MyCanvas() {
super();
}

public void setImage(Image i) {


image = i;
repaint();
}

public void paint(Graphics g) {


if (image != null)
g.drawImage(image, 0,0, this);
}
}

NOTE : You can download this example here

[applet version]

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

Have a simple Image browser 73


Real's HowTo PDF version

import java.net.*;
import java.io.*;

public class ImageBrowserApplet extends Applet {


public void init() {
APanel p = new APanel(this);
setLayout(new BorderLayout());
add(p, "Center");
}
}

class APanel extends Panel implements ActionListener {


private List lbx;
private MyCanvas can;
private Applet parent = null;
private String url[] = new String[50];

public APanel(Applet a) {
parent = a;
setLayout(new GridLayout(1,2));
lbx = new List();
can = new MyCanvas();
add(lbx); add(can);
initLbx();
// action on listbox double click
lbx.addActionListener(this);
setBackground(new Color(0).white);
}

public void actionPerformed (ActionEvent ae) {


try {
URL theUrl =
new URL(parent.getCodeBase(), url[lbx.getSelectedIndex()]);
MediaTracker media = new MediaTracker(this);
Image image =
Toolkit.getDefaultToolkit().getImage(theUrl);
media.addImage(image, 0);
media.waitForID(0);
can.setImage(image);
}
catch (Exception e) { e.printStackTrace();}
}

public void initLbx() {


int i = 0;
try {
String aLine = "";
URL source =
new URL(parent.getCodeBase(), "imagelist.txt");
BufferedReader in
= new BufferedReader
(new InputStreamReader(source.openStream()));;
while(null != (aLine = in.readLine())) {
java.util.StringTokenizer st =

Have a simple Image browser 74


Real's HowTo PDF version

new java.util.StringTokenizer(aLine, "|");


url[i++] = st.nextToken();
// lbx.addItem(st.nextToken());
lbx.add(st.nextToken());
}
}
catch(Exception e) { e.printStackTrace();}
}
}

class MyCanvas extends Canvas {


private Image image;
public MyCanvas() {
super();
}

public void setImage(Image i) {


image = i;
repaint();
}

public void paint(Graphics g) {


if (image != null)
g.drawImage(image, 0,0, this);
}
}

NOTE : You can try this example here

Simulate a "mouse over" event to toggle an image


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0264.html

Use a special Canvas to preload 2 GIFs, and using a MouseListener simply toggle the image.

[JDK1.1]

import java.awt.*;
import java.awt.event.*;
import java.net.*;

public class ToggleGifCanvas extends Canvas


implements MouseListener {
Image img1, img2;
int index = 0;
MediaTracker tracker;

public ToggleGifCanvas(URL n1, URL n2) {


tracker = new MediaTracker(this);
try {

Simulate a "mouse over" event to toggle an image 75


Real's HowTo PDF version

img1 = Toolkit.getDefaultToolkit().getImage(n1);
img2 = Toolkit.getDefaultToolkit().getImage(n2);
tracker.addImage(img1,0);
tracker.addImage(img2,1);
tracker.waitForAll();
addMouseListener(this);
}
catch (Exception e) {
e.printStackTrace();
}
}

public void paint(Graphics g) {


if (img1 != null) {
if (index == 0) {
g.drawImage(img1,0,0,this);
index++;
}
else {
g.drawImage(img2,0,0,this);
index--;
}
}
}

public Dimension getPreferredSize (){


return new Dimension
(img1.getHeight(this), img2.getWidth(this));
}

public void mouseClicked(MouseEvent e) {}


public void mousePressed(MouseEvent e) {}
public void mouseReleased(MouseEvent e) {}
public void mouseEntered(MouseEvent e) {
index = 1;
repaint();
}
public void mouseExited(MouseEvent e) {
index = 0;
repaint();
}
}

To use such Canvas, try something like this. This example needs our Gumby GIFs ( and ).

import java.applet.*;
import java.awt.*;
import java.net.*;

public class TestToogleGifCanvas extends Applet {


ToggleGifCanvas tgc;

public void init() {

Simulate a "mouse over" event to toggle an image 76


Real's HowTo PDF version

try {
tgc = new ToggleGifCanvas
(new URL(getDocumentBase(),"images/gumby.gif"),
new URL(getDocumentBase(),"images/gumby2.gif"));
add(tgc);
}
catch (Exception e) {
e.printStackTrace();
}
}
}

Try it here.

Hide the mouse cursor


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0440.html

One way is to use a transparent GIF as the cursor or create one.

int[] pixels = new int[16 * 16];


Image image = Toolkit.getDefaultToolkit().createImage(
new MemoryImageSource(16, 16, pixels, 0, 16));
Cursor transparentCursor =
Toolkit.getDefaultToolkit().createCustomCursor
(image, new Point(0, 0), "invisibleCursor");

Make a color transparent


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0265.html

Here we have an Image with a blue background like and we want to display it in an Applet with a white
background. All we have to do is to look for the blue color with the "Alpha bits" set to opaque and make them
transparent.

[Transparency.java]

import java.awt.*;
import java.awt.image.*;

public class Transparency {


public static Image makeColorTransparent
(Image im, final Color color) {
ImageFilter filter = new RGBImageFilter() {

Hide the mouse cursor 77


Real's HowTo PDF version

// the color we are looking for... Alpha bits are set to opaque
public int markerRGB = color.getRGB() | 0xFF000000;

public final int filterRGB(int x, int y, int rgb) {


if ( ( rgb | 0xFF000000 ) == markerRGB ) {
// Mark the alpha bits as zero - transparent
return 0x00FFFFFF & rgb;
}
else {
// nothing to do
return rgb;
}
}
};

ImageProducer ip = new FilteredImageSource(im.getSource(), filter);


return Toolkit.getDefaultToolkit().createImage(ip);
}
}

[app.java]

import java.awt.image.*;
import java.awt.*;
import java.net.*;

public class app extends java.applet.Applet {


Image GifOriginalWithWithBlueBackground;
Image GifModifiedWithTransparentBackground;

public void init() {


setBackground(new Color(0).white);

MediaTracker media = new MediaTracker(this);


// image of our friend, Gumby with a blue background
GifOriginalWithWithBlueBackground =
getImage(getDocumentBase(),"gumbyblu.gif");
media.addImage(GifOriginalWithWithBlueBackground,0);
try {
media.waitForID(0);
GifModifiedWithTransparentBackground =
Transparency.makeColorTransparent
(GifOriginalWithWithBlueBackground, new Color(0).blue);
}
catch(InterruptedException e) {}
}

public void paint(Graphics g) {


g.drawImage(GifOriginalWithWithBlueBackground, 10,10,this);
g.drawImage(GifModifiedWithTransparentBackground,10, 80,this);
}
}

Make a color transparent 78


Real's HowTo PDF version

[x.html]

<HTML><HEAD></HEAD><BODY>
<APPLET CODE="app.class"
NAME="myApplet"
HEIGHT=200 WIDTH=200>
</APPLET>
</BODY></HTML>

Save an Image as a GIF or JPEG file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0266.html

Take a look at the following package :

http://www.obrador.com/essentialjpeg/jpeg.htm for JPEG


http://www.acme.com for GIF
http://rsb.info.nih.gov/ij/ can display BMP and save as GIF or TIFF

With JDK1.2, Sun introduces a new package called JIMI (available for download at their Web site. With this
package, it's easy to convert a Java Image to a JPEG image file.

double w = 200.0;
double h = 200.0;
BufferedImage image = new BufferedImage(
(int)w,(int)h,BufferedImage.TYPE_INT_RGB);

Graphics2D g = (Graphics2D)image.getGraphics();
g.drawLine(0,0,w,h);

try {
File f = new File("myimage.jpg");
JimiRasterImage jrf = Jimi.createRasterImage(image.getSource());
Jimi.putImage("image/jpeg",jrf,new FileOutputStream(f));
}
catch (JimiException je) {
je.printStackTrace();}

Another way is to use the undocumented com.sun.image.codec.jpeg package.

// [JDK1.2]
// img is a Java Image
//
BufferedImage bimg = null;
int w = img.getWidth(null);
int h = img.getHeight(null);
int [] pixels = new int[w * h];
PixelGrabber pg = new PixelGrabber(img,0,0,w,h,pixels,0,w);

Save an Image as a GIF or JPEG file 79


Real's HowTo PDF version

try {
pg.grabPixels();
}
catch(InterruptedException ie) {
ie.printStackTrace();
}

bimg = new BufferedImage(w,h,BufferedImage.TYPE_INT_RGB);


bimg.setRGB(0,0,w,h,pixels,0,w);

// Encode as a JPEG
FileOutputStream fos = new FileOutputStream("out.jpg");
JPEGImageEncoder jpeg = JPEGCodec.createJPEGEncoder(fos);
jpeg.encode(bimg);
fos.close();

Since JDK1.4.2, javax.imageio.ImageIO lets you save and restore Images to disk in a platform independent
format. "png" and "jpeg" format are supported. With ImageIO, instead of Image you use BufferedImage
which is a subclass of Image.

import java.io.*;
import javax.imageio.*;
import java.awt.image.*;

public class FileOperations {

public static BufferedImage readImageFromFile(File file)


throws IOException
{
return ImageIO.read(file);
}

public static void writeImageToJPG


(File file,BufferedImage bufferedImage)
throws IOException
{
ImageIO.write(bufferedImage,"jpg",file);
}
}

Use the same background color as the browser


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0234.html

// in the HTML, use


// PARAM NAME="bgColor" VALUE="B8B5AE"
// (where VALUE is the same hexadecimal value
// as the HTML COLOR value)

Use the same background color as the browser 80


Real's HowTo PDF version

// in the APPLET tag


// in the JAVA init method :
Color bgcolor = new Color(
Integer.valueOf(getParameter("BGCOLOR"), 16).intValue());
setBackground(bgcolor);

Do simple animation using Images


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0262.html

By using a Thread, we switch between 2 GIFs ( and )

import java.applet.*;
import java.awt.*;
import java.awt.image.*;
import java.net.*;

public class AnimationGifApplet extends Applet {


Image [] img;
int index = 0;
int maxImg;
MediaTracker tracker;

public void init() {


img = new Image[2]; // 2 images in animation
maxImg = img.length - 1;
tracker = new MediaTracker(this);
try {
// images loading
img[0] = getImage(new URL(getDocumentBase(), "images/gumby.gif"));
img[1] = getImage(new URL(getDocumentBase(), "images/gumby2.gif"));
tracker.addImage(img[0],0);
tracker.addImage(img[1],1);
tracker.waitForAll();
}
catch (Exception e) {
e.printStackTrace();
}

AnimationThread at = new AnimationThread();


at.delayedAnimation(this, 500);
at.start();
}

public void paint(Graphics g) {


if (img[0] != null) {
g.drawImage(img[index],0,0,this);
index = (index <maxImg) ? index + 1 : 0;
}

Do simple animation using Images 81


Real's HowTo PDF version

public void animate() {


repaint();
}

class AnimationThread extends Thread {


AnimationGifApplet animationApplet;
int delay;

public void delayedAnimation(AnimationGifApplet a, int delay) {


this.animationApplet = a;
this.delay = delay;
}

public void run() {


while (true) {
try {
sleep(delay);
animationApplet.animate();
}
catch (Exception e) {
e.printStackTrace();
}
}
}
}
}

Try it here.

Do simple animation to show "work in progress"


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0263.html

Like the previous How-to, using a Thread, we switch between 2 GIFs, for example ( and ).

Click the button to simulate some work, click again to terminate the "work in progress"

[JDK1.1]

import java.applet.*;
import java.awt.*;
import java.awt.image.*;
import java.awt.event.*;
import java.net.*;

public class AnimationProgress extends Applet

Do simple animation to show "work in progress" 82


Real's HowTo PDF version

implements ActionListener{
Image [] img;
int index = 0;
int maxImg;
boolean working = false;
Button b;
MediaTracker tracker;

public void init() {


setLayout(new FlowLayout(FlowLayout.LEFT));
add(b = new Button("Working"));
b.addActionListener(this);
img = new Image[2]; // 2 images in animation
maxImg = img.length - 1;
tracker = new MediaTracker(this);
try {
// images loading
img[0] = getImage(new URL(getDocumentBase(), "gumby.gif"));
img[1] = getImage(new URL(getDocumentBase(), "gumby2.gif"));
tracker.addImage(img[0],0);
tracker.addImage(img[1],1);
tracker.waitForAll();
}
catch (Exception e) {
e.printStackTrace();
}

AnimationThread at = new AnimationThread();


at.delayedAnimation(this, 500);
at.start();
}

public void paint(Graphics g) {


if (img[0] != null) {
if (working) {
g.drawImage(img[index],68,0,this);
index = (index <maxImg) ? index + 1 : 0;
}
}
}

public void animate() {


repaint();
}

public void actionPerformed(ActionEvent ae) {


working = !working;
}

class AnimationThread extends Thread {


AnimationProgress animationApplet;
int delay;

public void delayedAnimation(AnimationProgress a, int delay) {

Do simple animation to show "work in progress" 83


Real's HowTo PDF version

this.animationApplet = a;
this.delay = delay;
}

public void run() {


while (true) {
try {
sleep(delay);
animationApplet.animate();
}
catch (Exception e) {
e.printStackTrace();
}
}
}
}
}

Get the color of a specific pixel


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0257.html

We assume that we have an Image called picture

pixels = new int[width*height];


PixelGrabber pg =
new PixelGrabber(picture, 0, 0, width, height, pixels, 0, width);
try {
pg.grabPixels();
}
catch (InterruptedException e) { }

From here, individual pixel can be accessed via the pixels array.

int c = pixels[index]; // or pixels[x * width + y]


int red = (c & 0x00ff0000) >> 16;
int green = (c & 0x0000ff00) >> 8;
int blue = c & 0x000000ff;
// and the Java Color is ...
Color color = new Color(red,green,blue);

Here another way to achieve this

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage

...

BufferedImage image = ImageIO.read(urlImage);

Get the color of a specific pixel 84


Real's HowTo PDF version

int c = image.getRGB(x,y);
int red = (c & 0x00ff0000) >> 16;
int green = (c & 0x0000ff00) >> 8;
int blue = c & 0x000000ff;
// and the Java Color is ...
Color color = new Color(red,green,blue);

Do "rubber-band" drawing
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0251.html

import java.applet.*;
import java.awt.*;
import java.util.Vector;

public class SimpleCAD extends Applet {


int w = 200;
int h = 200;
Vector lines = new Vector();
int np = 0;
int x1,y1;
int x2,y2;
int xl,yl;
Image offImg;
Graphics offGra;
Button btnClear, btnUndo;

public void init() {


setLayout(new FlowLayout());
btnClear = new Button("Clear");
btnUndo = new Button("Undo");
add(btnClear);
add(btnUndo);
setBackground(new Color(0).black);
setForeground(new Color(0).white);
}

public void Dragupdate(Graphics g) {


/*
** rubber-band effect
*/
g.setXORMode(getBackground());
setForeground(new Color(0).blue);
if (xl != -1){
// erase the old line
g.drawLine(x1, y1, xl, yl);
if (x2 != -1) {
// draw the new one
g.drawLine(x1, y1, x2, y2);

Do "rubber-band" drawing 85
Real's HowTo PDF version

}
}
}

public void update(Graphics g) {


// draw an offScreen drawing
Dimension dim = getSize();
if (offGra == null) {
offImg = createImage(dim.width, dim.height);
offGra = offImg.getGraphics();
}
offGra.setColor(new Color(0).black);
offGra.fillRect(0,0,dim.width, dim.height);
offGra.setColor(new Color(0).white);
offGra.setPaintMode();
for (int i=0; i < np; i++) {
Rectangle p = (Rectangle)lines.elementAt(i);
if (p.width != -1) {
offGra.drawLine(p.x, p.y, p.width, p.height);
}
}
// put the OffScreen image OnScreen
g.drawImage(offImg,0,0,null);
}

public boolean handleEvent(Event e) {


switch (e.id) {
case Event.MOUSE_DOWN:
// new starting point
x1 = e.x;
y1 = e.y;
// begin an new drawing process
x2 = -1;
return true;
case Event.MOUSE_UP:
// end a drawing process
lines.addElement(new Rectangle(x1, y1, e.x, e.y));
np++;
x2 = xl = -1;
repaint();
return true;
case Event.MOUSE_DRAG:
// xl yl line to be erased
xl = x2;
yl = y2;
// x2 y2 last current point
x2 = e.x;
y2 = e.y;
Dragupdate(getGraphics());
return true;
}
return super.handleEvent(e);
}

Do "rubber-band" drawing 86
Real's HowTo PDF version

public boolean action(Event e, Object o) {


if (e.target == btnClear) resetDrawing();
if (e.target == btnUndo) undo();
return true;
}

public void undo() {


if (np>0) {
lines.removeElementAt(np-1);
np--;
repaint();
}
}

public void resetDrawing() {


lines.removeAllElements();
np=0;
repaint();
}
}

Convert RGB value to Hex (to be used in HTML)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0255.html

import java.awt.*;
public class Color2Hex {
public static void main( String[] args ) {
if (args.length != 3) {
System.out.println("Color2Hex r g b");
}
else {
int i = Integer.parseInt(args[0]);
int j = Integer.parseInt(args[1]);
int k = Integer.parseInt(args[2]);

Color c = new Color(i,j,k);


System.out.println
( "hex: " + Integer.toHexString( c.getRGB() & 0x00ffffff ) );
}
}
}

Draw a line or set a pixel in my own image


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0250.html

Convert RGB value to Hex (to be used in HTML) 87


Real's HowTo PDF version

import java.awt.image.*;
import java.awt.*;
import java.applet.*;

public class CreateAnImage extends Applet {


Image myImage;

public void init() {


int x = 100;
int y = 100;
myImage = createImage(x,y);
Graphics g = myImage.getGraphics();
g.drawLine(0,0,x,y);
g.drawLine(x,0,0,y);
for(int i=0; i <x; i+=2){
setPixel(myImage, 50, i, new Color(0).blue);
setPixel(myImage, i, 50, new Color(0).green);
}
}

public void paint(Graphics g) {


g.drawImage(myImage,0,0,this);
}

public void setPixel


(Image image, int x, int y, Color color ) {
Graphics g = image.getGraphics( );
g.setColor( color );
g.fillRect( x, y, 1, 1 );
g.dispose( );
}
}

Draw dashed line


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0224.html

public void drawDashedLine(Graphics g,int x1,int y1,int x2,int y2,


double dashlength, double spacelength) {
if((x1==x2)&&(y1==y2)) {
g.drawLine(x1,y1,x2,y2);
return;
}
double linelength=Math.sqrt((x2-x1)*(x2-x1)+(y2-y1)*(y2-y1));
double yincrement=(y2-y1)/(linelength/(dashlength+spacelength));
double xincdashspace=(x2-x1)/(linelength/(dashlength+spacelength));
double yincdashspace=(y2-y1)/(linelength/(dashlength+spacelength));

Draw a line or set a pixel in my own image 88


Real's HowTo PDF version

double xincdash=(x2-x1)/(linelength/(dashlength));
double yincdash=(y2-y1)/(linelength/(dashlength));
int counter=0;
for (double i=0;i<linelength-dashlength;i+=dashlength+spacelength){
g.drawLine((int) (x1+xincdashspace*counter),
(int) (y1+yincdashspace*counter),
(int) (x1+xincdashspace*counter+xincdash),
(int) (y1+yincdashspace*counter+yincdash));
counter++;
}
if ((dashlength+spacelength)*counter<=linelength)
g.drawLine((int) (x1+xincdashspace*counter),
(int) (y1+yincdashspace*counter),
x2,y2);
}

Draw a line with a thickness


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0260.html

import java.awt.*;
import java.applet.*;

public class thickLine extends Applet {

public void init( ) { }

public void paint( Graphics g ) {


drawThickLine
(g, 0, 0, getSize().width, getSize().height, 5, new Color(0).black);
drawThickLine
(g, 0, getSize().height, getSize().width, 0, 5, new Color(0).red);

drawThickLine
(g, getSize().width/2, 0, getSize().width/2, getSize().height, 8,
new Color(0).green);
drawThickLine
(g, 0, getSize().height/2, getSize().width, getSize().height/2, 12,
new Color(0).blue);
}

public void drawThickLine(


Graphics g, int x1, int y1, int x2, int y2, int thickness, Color c) {
// The thick line is in fact a filled polygon
g.setColor(c);
int dX = x2 - x1;
int dY = y2 - y1;
// line length
double lineLength = Math.sqrt(dX * dX + dY * dY);

Draw dashed line 89


Real's HowTo PDF version

double scale = (double)(thickness) / (2 * lineLength);

// The x,y increments from an endpoint needed to create a rectangle...


double ddx = -scale * (double)dY;
double ddy = scale * (double)dX;
ddx += (ddx > 0) ? 0.5 : -0.5;
ddy += (ddy > 0) ? 0.5 : -0.5;
int dx = (int)ddx;
int dy = (int)ddy;

// Now we can compute the corner points...


int xPoints[] = new int[4];
int yPoints[] = new int[4];

xPoints[0] = x1 + dx; yPoints[0] = y1 + dy;


xPoints[1] = x1 - dx; yPoints[1] = y1 - dy;
xPoints[2] = x2 - dx; yPoints[2] = y2 - dy;
xPoints[3] = x2 + dx; yPoints[3] = y2 + dy;

g.fillPolygon(xPoints, yPoints, 4);


}
}

Using JDK1.2

public void paint(Graphics g){


Graphics2D g2d = (Graphics2D)g;
int width = 10;
g2d.setStroke(new BasicStroke(width));
g2d.drawLine(x1, y1, x2, y2);
}

On a Component

int width = 10;


BasicStroke bs = new BasicStroke(width);
JLabel l = new JLabel();
l.getGraphics().setStroke(bs);
l.drawLine(0,0,100,100);

Using JDK1.3

import javax.swing.*;
import java.awt.*;
import java.awt.geom.*;

public class TestLine extends JFrame{


private MyPanel panel;
public TestLine() {
setSize(200, 200);
panel = new MyPanel();
getContentPane().add( panel, "Center" );

Draw a line with a thickness 90


Real's HowTo PDF version

public static void main( String [] args ){


TestLine tl = new TestLine();
tl.setVisible( true );
}
}

class MyPanel extends JPanel {


final static BasicStroke stroke = new BasicStroke(2.0f);
final static BasicStroke wideStroke = new BasicStroke(8.0f);

public MyPanel(){}

public void paintComponent( Graphics g ){


Graphics2D g2 = (Graphics2D)g;
g2.setRenderingHint
(RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
g2.setStroke( stroke );
g2.draw(new Line2D.Double(10.0, 10.0, 100.0, 10.0));
g2.setStroke( wideStroke );
g2.draw(new Line2D.Double(10.0, 50.0, 100.0, 50.0));
}
}

Draw a pie chart


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0261.html

import java.util.*;
import java.awt.*;
import java.applet.Applet;

public class Graph extends Applet {


int depth, radius;

public void init() {


float value;
String at = getParameter("width");
radius = (at != null) ? Integer.valueOf(at).intValue() : 100;
at = getParameter("depth");
depth = (at != null) ? Integer.valueOf(at).intValue() : 20;
at = getParameter("values");
PieChartCanvas c = new PieChartCanvas(radius, depth);
setLayout(new BorderLayout());

// Create Hashtable to map color name (String) to Color type


Hashtable colors = new Hashtable();

Draw a pie chart 91


Real's HowTo PDF version

colors.put("green", Color.green);
colors.put("red", Color.red);
colors.put("blue", Color.blue);
colors.put("yellow", Color.yellow);
colors.put("magenta", Color.magenta);
colors.put("cyan", Color.cyan);
colors.put("orange", Color.orange);
colors.put("pink", Color.pink);
colors.put("white", Color.white);
colors.put("black", Color.black);

// "value-color,value-color,..."
StringTokenizer t = new StringTokenizer(at, ",");
String s;
int i;
while (t.hasMoreTokens()) {
s = t.nextToken();
i = s.indexOf('-');
value = Float.valueOf(s.substring(0, i)).floatValue();
c.addSlice(value, (Color)colors.get(s.substring(i + 1)));
}

resize(c.getMinimumSize().width, c.getMinimumSize().height);
add("Center", c);
}
}

class PieChartCanvas extends Canvas {


/*
** author Ciaran Treanor [email protected]
*/
final double aspectFudge = 2.5;
int radius, depth, called = 1, numSlices = 0;
float total = 0, value[] = new float[10];
Color color[] = new Color[10];
Graphics offGraphics;
Image gfxBuff;

public PieChartCanvas(int radius, int depth) {


this.value = value;
this.color = color;
this.radius = radius;
this.depth = depth;
}

public void paint(Graphics g) {


int startAngle;
float angle;
Dimension d = getSize();

if(gfxBuff == null) {
gfxBuff = createImage(d.width, d.height);
offGraphics = gfxBuff.getGraphics();
offGraphics.setColor(getBackground());

Draw a pie chart 92


Real's HowTo PDF version

offGraphics.fillRect(0, 0, d.width, d.height);


}

// do the 3d effect
for(int x = depth; x >= 1; x--) {
startAngle = -45;
for(int i = 0; i < numSlices; i++) {
offGraphics.setColor(color[i].darker());
angle = Math.round(360 * (value[i] / total));
offGraphics.fillArc(0, x, radius, (int)(radius / aspectFudge),
startAngle, (int)angle);
startAngle += angle;
}
}

// draw the pie slice


startAngle = -45;
for(int i = 0; i < numSlices; i++) {
offGraphics.setColor(color[i]);
angle = Math.round(360 * (value[i] / total));
offGraphics.fillArc(0, 0, radius, (int)(radius / aspectFudge),
startAngle, (int)angle);
startAngle += angle;
}
g.drawImage(gfxBuff, 0, 0, null);
}

public void addSlice(float value, Color color) {


this.value[numSlices] = value;
this.color[numSlices++] = color;
total += value;
}

public Dimension getPreferredSize() {


return getMinimumSize();
}

public Dimension getMinimumSize() {


return new Dimension(radius, (int)((radius / aspectFudge) + depth));
}
}

[JavaPie.hmtl]

<HTML>
<TABLE><TR><TD>
<APPLET CODE=Graph.class WIDTH=150 HEIGHT=150>
<PARAM NAME="depth" VALUE="30">
<PARAM NAME="width" VALUE="120">
<PARAM NAME="values" VALUE="1-red,5-green,7-blue">
</APPLET>
<TD>
<TABLE>
<TR><TD>item 1<TD BGCOLOR="#FF0000">

Draw a pie chart 93


Real's HowTo PDF version

<TR><TD>item 2<TD BGCOLOR="#008000">


<TR><TD>item 3<TD BGCOLOR="#0000FF">
</TABLE>
</TABLE>
</HMTL>

Try it here

Draw faster rectangles


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0364.html

Thanks to Chikirev Sergey

It seems that drawRoundRect(.) is 1,5 faster then drawRect(..) , because one of them is completely native.

import java.awt.*;
import java.awt.event.*;

public class Class1 extends Frame implements ActionListener{


public void paint(Graphics g){
super.paint(g);
long t=System.currentTimeMillis();
for(int i=0;i<10000;i++){
g.drawRect(10,70,100,50);
}
t=System.currentTimeMillis()-t;
g.drawString(String.valueOf(t),10,70);
t=System.currentTimeMillis();
for(int i=0;i<10000;i++){
g.drawRoundRect(10,130,100,50,0,0);
}
t=System.currentTimeMillis()-t;
g.drawString(String.valueOf(t),10,130);
}

public void actionPerformed(ActionEvent p1){


repaint(0,10,200,300);
}

public static void main (String[] args){


Class1 c=new Class1();
c.setSize(300,300);
c.setLayout(new BorderLayout());
Button b=new Button("Refresh");
c.add(BorderLayout.SOUTH , b);
b.addActionListener(c);
c.show();
}
}

Draw faster rectangles 94


Real's HowTo PDF version

Get a screen capture and save it as a JPEG


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0489.html

The screen capture is done with java.awt.Robot.

import java.awt.AWTException;
import java.awt.Robot;
import java.awt.Rectangle;
import java.awt.Toolkit;
import java.awt.image.BufferedImage;
import java.io.*;
import javax.imageio.ImageIO;

class ScreenCapture {
public static void main(String args[]) throws
AWTException, IOException {
// capture the whole screen
BufferedImage screencapture = new Robot().createScreenCapture(
new Rectangle(Toolkit.getDefaultToolkit().getScreenSize()) );

// Save as JPEG
File file = new File("screencapture.jpg");
ImageIO.write(screencapture, "jpg", file);

// Save as PNG
// File file = new File("screencapture.png");
// ImageIO.write(screencapture, "png", file);
}
}

To capture a specific area

BufferedImage screencapture = new Robot().createScreenCapture(


new Rectangle( 15, 15, 150, 150));

To capture a specific visual object

BufferedImage image = new Robot().createScreenCapture(


new Rectangle( myframe.getX(), myframe.getY(),
myframe.getWidth(), myframe.getHeight() ) );

Detect a double click versus a simple click


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0235.html

Get a screen capture and save it as a JPEG 95


Real's HowTo PDF version

[JDK1.02]

import java.applet.*;
import java.awt.*;

public class d extends Applet {

int dClkRes = 300; // double-click speed in ms


long timeMouseDown=0; // last mouse down time
int lastX=0,lastY=0; // last x and y

public boolean mouseDown(Event event, int x, int y){


/*
** check for double click
*/
long currentTime = event.when;
if ((lastX==x) && (lastY==y) &&
((event.when-timeMouseDown) < dClkRes)) {
System.out.println("double click " + currentTime);
return false;
}
else {
//single click action could be added here
System.out.println("simple click " + currentTime);
timeMouseDown = event.when;
lastX=x;
lastY=y;
}
return true;
}
}

[JDK11]

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

public class d extends Applet


implements MouseListener {

public void init() {


this.addMouseListener(this);
}

public void paint(Graphics g) {


g.drawString("Click here", 10,10);
}

public void mousePressed(MouseEvent e) {}


public void mouseReleased(MouseEvent e) {}
public void mouseEntered(MouseEvent e) {}

Detect a double click versus a simple click 96


Real's HowTo PDF version

public void mouseExited(MouseEvent e) {}


public void mouseClicked(MouseEvent e) {
System.out.println
( "Click at (" + e.getX() + ":" + e.getY() + ")" );
if (e.getClickCount() == 2)
System.out.println( " and it's a double click!");
else
System.out.println( " and it's a simple click!");
}
}

Detect the mouse button used when clicking


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0236.html

[JDK11]

import java.applet.*;
import java.awt.*;
import java.awt.event.*;

public class d extends Applet


implements MouseListener {

public void init() {


this.addMouseListener(this);
}

public void paint(Graphics g) {


g.drawString("Click here", 10,10);
}

public void mousePressed(MouseEvent e) {}


public void mouseReleased(MouseEvent e) {}
public void mouseEntered(MouseEvent e) {}
public void mouseExited(MouseEvent e) {}
public void mouseClicked(MouseEvent e) {
switch(e.getModifiers()) {
case InputEvent.BUTTON1_MASK: {
System.out.println("That's the LEFT button");
break;
}
case InputEvent.BUTTON2_MASK: {
System.out.println("That's the MIDDLE button");
break;
}
case InputEvent.BUTTON3_MASK: {
System.out.println("That's the RIGHT button");
break;
}

Detect the mouse button used when clicking 97


Real's HowTo PDF version

}
}
}

Exit an application from a menu (single exit point)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0276.html

import java.awt.*;
import java.awt.event.*;

public class ExitFromMenu extends Frame implements ActionListener {


Menu m = new Menu("Exit From Here");

ExitFromMenu() {
super("");
MenuBar mb = new MenuBar();

mb.add(m);
MenuItem m1 = m.add(new MenuItem("Exit",
new MenuShortcut(KeyEvent.VK_X)));
m1.setActionCommand("Exit");
m.addActionListener(this);

setMenuBar(mb);

addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
// unique exit point
System.out.println("Bye.");
System.exit(0);
}
}
);
add(new Label
("You can quit by clicking on the 'X'"),"South");
add(new Label
("You can quit by clicking on the menu item 'Exit'"),"Center");
add(new Label
("You can quit with the MenuShortcut 'ctrl-x'"),"North");
setSize(300, 300);
show();
}

public void actionPerformed(ActionEvent evt) {


String what = evt.getActionCommand();

if (what.equals("Exit"))

Exit an application from a menu (single exit point) 98


Real's HowTo PDF version

processEvent(new WindowEvent(this, WindowEvent.WINDOW_CLOSING));


}

static public void main(String[] args) {


new ExitFromMenu();
}
}

Trigger a click on a Button


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0468.html

In this example, when we click on a Button, we trigger the action attached to the another Button.

Regular AWT (applet)

import java.awt.*;
import java.awt.event.*;
import java.applet.*;

public class TestEvent extends Applet implements ActionListener {


Button b2, b1;
TextField t1;

public void init() {


setLayout(new FlowLayout());
t1 = new TextField(30);
b1 = new Button("Output");
add(b1); add(t1);
b2 = new Button("Fire event 1st button");
add(b2);

b1.addActionListener(this);
b2.addActionListener(this);

public void actionPerformed(ActionEvent e) {


if (e.getSource() == b1) {
t1.setText("1st button clicked");
}
if (e.getSource() == b2) {
// from the b2 button, we creating an event to trigger a click
// on the b1 button
ActionEvent ae =
new ActionEvent((Object)b1, ActionEvent.ACTION_PERFORMED, "");
Toolkit.getDefaultToolkit().getSystemEventQueue().postEvent(ae);
// b1.dispatchEvent(ae); can be used too.
}
}

Trigger a click on a Button 99


Real's HowTo PDF version

With Swing (japplet)

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class TestEventSwing extends JApplet implements ActionListener {


JButton b1, b2;
JTextField t1;

public void init() {


setLayout(new FlowLayout());
t1 = new JTextField(30);
b1 = new JButton("Output");
add(b1); add(t1);
b2 = new JButton("Fire event 1st button");
add(b2);

b1.addActionListener(this);
b2.addActionListener(this);
}

public void actionPerformed(ActionEvent e) {


if (e.getSource() == b1) {
t1.setText("first button clicked");
}
if (e.getSource() == b2) {
// from the b2 button, we trigger a click on the b1 button.
// As an added bonus, we have visual effect on b1!
b1.doClick();
}
}
}

Display a TIF
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0605.html

The regular JDK can only deal with JPG, GIF, BMP or PNG file with the package ImageIO, see this HowTo.

To deal with TIF file, you must use the JAI (Java Advanced Imaging) package.

This example will display a given TIF file. It will also display other types (JPG,...) by detecting the type.

import javax.media.jai.PlanarImage;
import com.sun.media.jai.codec.ByteArraySeekableStream;
import com.sun.media.jai.codec.ImageCodec;

Display a TIF 100


Real's HowTo PDF version

import com.sun.media.jai.codec.ImageDecoder;
import com.sun.media.jai.codec.SeekableStream;
import java.io.FileInputStream;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.awt.Image;
import java.awt.image.RenderedImage;

import javax.swing.JOptionPane;
import javax.swing.JLabel;
import javax.swing.ImageIcon;

public class ImageViewer {

static Image load(byte[] data) throws Exception{


Image image = null;
SeekableStream stream = new ByteArraySeekableStream(data);
String[] names = ImageCodec.getDecoderNames(stream);
ImageDecoder dec =
ImageCodec.createImageDecoder(names[0], stream, null);
RenderedImage im = dec.decodeAsRenderedImage();
image = PlanarImage.wrapRenderedImage(im).getAsBufferedImage();
return image;
}

public static void main(String[] args) throws Exception{


String path;
if (args.length==0) {
path = JOptionPane.showInputDialog(null, "Image Path",
"c:/applications/sidebar.tif");
}
else {
path = args[0];
}
FileInputStream in = new FileInputStream(path);
FileChannel channel = in.getChannel();
ByteBuffer buffer = ByteBuffer.allocate((int)channel.size());
channel.read(buffer);
Image image = load(buffer.array());
// make sure that the image is not too big
// scale with a width of 500
Image imageScaled =
image.getScaledInstance(500, -1, Image.SCALE_SMOOTH);
//
System.out.println("image: " + path + "\n" + image);
//
JOptionPane.showMessageDialog(null, new JLabel(
new ImageIcon( imageScaled )) );
}
}

The JAI package is composed of 2 jars : jai_core.jar and jai_codec.jar

Display a TIF 101


Real's HowTo PDF version

http://java.sun.com/javase/technologies/desktop/media/jai/
https://jai.dev.java.net/#Downloads

To write a TIF file, see this HowTo

Convert a multi-page TIF into single-page TIF


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0535.html

Tagged Image File Format (abbreviated TIFF) is a file format for mainly storing images, including
photographs and line art. TIFF was originally created as an attempt to get desktop scanner vendors of the
mid-1980's to agree on a common scanned image file format, rather than have each company promulgate its
own proprietary format.

This HowTo takes a multi-page TIF (from a FAX) and convert it into many single-pages TIF.

This is done with the JAI (Java Advance Image) package.

http://java.sun.com/products/java-media/jai/index.jsp

>
import java.io.*;

import com.sun.media.jai.codec.FileSeekableStream;
import com.sun.media.jai.codec.ImageDecoder;
import com.sun.media.jai.codec.ImageCodec;
import com.sun.media.jai.codec.TIFFEncodeParam;

import java.awt.image.RenderedImage;
import javax.media.jai.RenderedOp;
import javax.media.jai.JAI;
import java.awt.image.renderable.ParameterBlock;

public class TestTiff {

public static void main(String[] args) throws IOException {


new TestTiff().doitJAI();
}

public void doitJAI() throws IOException {


FileSeekableStream ss = new FileSeekableStream("d:/multi.tif");
ImageDecoder dec = ImageCodec.createImageDecoder("tiff", ss, null);
int count = dec.getNumPages();
TIFFEncodeParam param = new TIFFEncodeParam();
param.setCompression(TIFFEncodeParam.COMPRESSION_GROUP4);
param.setLittleEndian(false); // Intel

Convert a multi-page TIF into single-page TIF 102


Real's HowTo PDF version

System.out.println("This TIF has " + count + " image(s)");


for (int i = 0; i < count; i++) {
RenderedImage page = dec.decodeAsRenderedImage(i);
File f = new File("d:/single_" + i + ".tif");
System.out.println("Saving " + f.getCanonicalPath());
ParameterBlock pb = new ParameterBlock();
pb.addSource(page);
pb.add(f.toString());
pb.add("tiff");
pb.add(param);
RenderedOp r = JAI.create("filestore",pb);
r.dispose();
}
}
}

This solution is working but JAI is a slow performer.

You may want to consider to use an external utility to do this kind on conversion. A nice one is irfanview
(win), a (free) multi-purpose graphic utility.

http://www.irfanview.com/

To do a TIF conversion, use this command line :

C:\IrfanView\i_view32" d:\multi.tif /extract=(d:\,tif) /killmesoftly

irfanview is an amazing software when it comes to transform a graphic format to another one. You can use it
from a command line or from a GUI.

See also : Convert many single-page TIF into one multi-page TIF

Convert many single-page TIF into one multi-page TIF


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-convert-many-single-tif-into-one-multiple-page-tif.html

This HowTo takes a list of single-page TIF and convert them into one multi-page TIF.

This is done with the JAI (Java Advance Image) package.

import java.io.FileOutputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
import java.awt.image.BufferedImage;

import javax.media.jai.NullOpImage;

Convert many single-page TIF into one multi-page TIF 103


Real's HowTo PDF version

import javax.media.jai.OpImage;
import javax.media.jai.PlanarImage;

import com.sun.media.jai.codec.ImageEncoder;
import com.sun.media.jai.codec.SeekableStream;
import com.sun.media.jai.codec.FileSeekableStream;
import com.sun.media.jai.codec.ImageDecoder;
import com.sun.media.jai.codec.ImageCodec;
import com.sun.media.jai.codec.TIFFEncodeParam;

public class TiffUtils {

public static void main(String[] args) throws Exception {

// 2 single page TIF to be in a multipage


String [] tifs = {
"C:/temp/test01.tif",
"C:/temp/test02.tif"
};
int numTifs = tifs.length; // 2 pages

BufferedImage image[] = new BufferedImage[numTifs];


for (int i = 0; i < numTifs; i++) {
SeekableStream ss = new FileSeekableStream(tifs[i]);
ImageDecoder decoder = ImageCodec.createImageDecoder("tiff", ss, null);
PlanarImage pi = new NullOpImage
(decoder.decodeAsRenderedImage(0),null,null,OpImage.OP_IO_BOUND);
image[i] = pi.getAsBufferedImage();
ss.close();
}

TIFFEncodeParam params = new TIFFEncodeParam();


params.setCompression(TIFFEncodeParam.COMPRESSION_DEFLATE);
OutputStream out = new FileOutputStream("C:/temp/multipage.tif");
ImageEncoder encoder = ImageCodec.createImageEncoder("tiff", out, params);
List <BufferedImage>list = new ArrayList<BufferedImage>(image.length);
for (int i = 1; i < image.length; i++) {
list.add(image[i]);
}
params.setExtraImages(list.iterator());
encoder.encode(image[0]);
out.close();

System.out.println("Done.");
}
}

See also : Convert a multi-page TIF into single-page TIF

Convert an Image to a BufferedImage


Current version of this HowTo :

Convert an Image to a BufferedImage 104


Real's HowTo PDF version

http://www.rgagnon.com/javadetails/../javadetails/java-0601.html

import java.awt.*;
import java.awt.image.*;
import javax.imageio.*;
import java.io.*;

public class ImageUtils {

public static BufferedImage imageToBufferedImage(Image im) {


BufferedImage bi = new BufferedImage
(im.getWidth(null),im.getHeight(null),BufferedImage.TYPE_INT_RGB);
Graphics bg = bi.getGraphics();
bg.drawImage(im, 0, 0, null);
bg.dispose();
return bi;
}

public static BufferedImage readImageFromFile(File file)


throws IOException
{
return ImageIO.read(file);
}

public static void writeImageToPNG


(File file,BufferedImage bufferedImage)
throws IOException
{
ImageIO.write(bufferedImage,"png",file);
}

public static void writeImageToJPG


(File file,BufferedImage bufferedImage)
throws IOException
{
ImageIO.write(bufferedImage,"jpg",file);
}
}

You need to do something to transform an Image to BufferedImage. But since BufferedImage extends Image,
so there isn't a back-conversion, it's not needed.

Detect if a TIF is blank


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0631.html

Detect if a TIF is blank 105


Real's HowTo PDF version

import javax.media.jai.PlanarImage;
import com.sun.media.jai.codec.ByteArraySeekableStream;
import com.sun.media.jai.codec.ImageCodec;
import com.sun.media.jai.codec.ImageDecoder;
import com.sun.media.jai.codec.SeekableStream;
import java.io.FileInputStream;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.image.PixelGrabber;
import java.awt.image.BufferedImage;
import java.awt.image.RenderedImage;

/**
* This utility loads a given TIF and try to detect if it's
* blank or not.
*
* We create in-memory image and then calculate the standard
* deviation of the color information. If a certain value is not
* reached then we assume that the image is mainly uniform and
* probably blank. The threshold value is an estimate. Depending
* the source of the TIF this value can be higher. For example,
* TIF from a FAX machine or a scanner can be dirty, with hair/dust presence,
* but with no content.
*
* jai_core.jar and jai_codec.jar are required.
* http://java.sun.com/products/java-media/jai/index.jsp
*
* @author http://www.rgagnon.com/howto.html
*/

public class BlankDetection {

public static final int FAILURE = 2;


public static final int BLANK = 0;
public static final int NOTBLANK = 1;
// value where we can consider that this is a blank image
// can be much higher depending of the TIF source
// (ex. scanner or fax)
public static final int BLANK_THRESHOLD = 1000;

/**
* Creates an Image from a byte array
* @param data
* @return Image
* @throws Exception
*/
public static Image load(byte[] data) throws Exception {
Image image = null;
SeekableStream stream = new ByteArraySeekableStream(data);
String[] names = ImageCodec.getDecoderNames(stream);
ImageDecoder dec =

Detect if a TIF is blank 106


Real's HowTo PDF version

ImageCodec.createImageDecoder(names[0], stream, null);


RenderedImage im = dec.decodeAsRenderedImage();
image = PlanarImage.wrapRenderedImage(im).getAsBufferedImage();
// scale-down the image , maximum width : 500 px
// to preserve memory
Image imageScaled =
image.getScaledInstance(500, -1, Image.SCALE_SMOOTH);
return imageScaled;
}

/**
* Converts an Image to a BufferedImage
* @param im une Image
* @return BufferedImage
*/
public static BufferedImage imageToBufferedImage(Image im) {
BufferedImage bi = new BufferedImage
(im.getWidth(null),im.getHeight(null),BufferedImage.TYPE_INT_RGB);
Graphics bg = bi.getGraphics();
bg.drawImage(im, 0, 0, null);
bg.dispose();
return bi;
}

/**
* Check if an Image is blank or not
* Computes the standard deviation based on the color information

* @param bi bufferedimage
* @return true it's blank
*/
public static boolean isBlank(BufferedImage bi) throws Exception {
long count = 0;
long total = 0;
double totalVariance = 0;
double stdDev = 0;
int height = bi.getHeight();
int width = bi.getWidth();

int[] pixels = new int[width * height];


PixelGrabber pg = new PixelGrabber
(bi, 0, 0, width, height, pixels, 0, width);
pg.grabPixels();
for (int j = 0; j < height; j++) {
for (int i = 0; i < width; i++) {
count++;
int pixel = pixels[j * width + i];
int red = (pixel >> 16) & 0xff;
int green = (pixel >> 8) & 0xff;
int blue = (pixel) & 0xff;
int pixelValue = new Color(red, green,blue,0).getRGB();
total += pixelValue;
double avg = total /count;
totalVariance += Math.pow(pixelValue - avg, 2);

Detect if a TIF is blank 107


Real's HowTo PDF version

stdDev = Math.sqrt(totalVariance / count);


}
}
return (stdDev <BLANK_THRESHOLD);
}

/**
* Accept on the command line the path to a TIF file
*
* Returns an errorlevel based on the analysis
* 0 - blank
* 1 - not blank
* 2 - IO error
*
* @param args path vers complet vers un PROPS
*/
public static void main(String[] args) {
try {
if (args.length==0) {
System.out.println("Missing parameter.");
System.exit(FAILURE);
}
String path = args[0];
FileInputStream in = new FileInputStream(path);
FileChannel channel = in.getChannel();
ByteBuffer buffer = ByteBuffer.allocate((int)channel.size());
channel.read(buffer);
Image image = load(buffer.array());
BufferedImage bufferedImage = imageToBufferedImage(image);
boolean isBlank = BlankDetection.isBlank(bufferedImage);

System.exit( isBlank ? BLANK : NOTBLANK );


}
catch (Exception e) {
e.printStackTrace();
System.exit(FAILURE);
}
}
}

Convert TIF to PDF


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0645.html

This HowTo is based on the iText package. You need a recent version (ex. 2.*)

This a command line utility. You pass one or many tif files as argument and corresponding PDF are produced.
Multipage TIF are supported. TIF are resized to fit a letter-page dimension.

Convert TIF to PDF 108


Real's HowTo PDF version

import java.io.FileOutputStream;

import com.lowagie.text.Document;
import com.lowagie.text.Image;
import com.lowagie.text.PageSize;
import com.lowagie.text.Rectangle;
import com.lowagie.text.pdf.PdfContentByte;
import com.lowagie.text.pdf.PdfWriter;
import com.lowagie.text.pdf.RandomAccessFileOrArray;
import com.lowagie.text.pdf.codec.TiffImage;

public class TiffToPDF {


public static void main(String[] args) {
if (args.length < 1) {
System.out
.println("Usage: Tiff2Pdf file1.tif [file2.tif ... fileN.tif]");
System.exit(1);
}
String tiff;
String pdf;
for (int i = 0; i < args.length; i++) {
tiff = args[i];
pdf = tiff.substring(0, tiff.lastIndexOf('.') + 1) + "pdf";
Document document = new Document(PageSize.LETTER, 0, 0, 0, 0);
try {
PdfWriter writer = PdfWriter.getInstance(document,
new FileOutputStream(pdf));
int pages = 0;
document.open();
PdfContentByte cb = writer.getDirectContent();
RandomAccessFileOrArray ra = null;
int comps = 0;
try {
ra = new RandomAccessFileOrArray(tiff);
comps = TiffImage.getNumberOfPages(ra);
}
catch (Throwable e) {
System.out.println("Exception in " + tiff + " "
+ e.getMessage());
continue;
}
System.out.println("Processing: " + tiff);
for (int c = 0; c < comps; ++c) {
try {
Image img = TiffImage.getTiffImage(ra, c + 1);
if (img != null) {
System.out.println("page " + (c + 1));
img.scalePercent
(7200f / img.getDpiX(), 7200f / img.getDpiY());
document.setPageSize
(new Rectangle(img.getScaledWidth(), img.getScaledHeight()));
img.setAbsolutePosition(0, 0);
cb.addImage(img);
document.newPage();

Convert TIF to PDF 109


Real's HowTo PDF version

++pages;
}
}
catch (Throwable e) {
System.out.println("Exception " + tiff + " page "
+ (c + 1) + " " + e.getMessage());
}
}
ra.close();
document.close();
}
catch (Throwable e) {
e.printStackTrace();
}
System.out.println("done");
}
}
}

Convert TIF to JPG


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-convert-tif-to-jpg.html

You need the Java Advanced Imaging (JAI) API.

http://java.sun.com/javase/technologies/desktop/media/jai/

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.awt.image.RenderedImage;
import com.sun.image.codec.jpeg.JPEGCodec;
import com.sun.image.codec.jpeg.JPEGImageEncoder;
import com.sun.media.jai.codec.SeekableStream;
import com.sun.media.jai.codec.FileSeekableStream;
import com.sun.media.jai.codec.TIFFDecodeParam;
import com.sun.media.jai.codec.ImageDecoder;
import com.sun.media.jai.codec.ImageCodec;

public class TiffUtils {

public static void TiffToJpg(String tiff, String output)


throws IOException
{
File tiffFile = new File(tiff);
SeekableStream s = new FileSeekableStream(tiffFile);
TIFFDecodeParam param = null;
ImageDecoder dec = ImageCodec.createImageDecoder("tiff", s, param);
RenderedImage op = dec.decodeAsRenderedImage(0);
FileOutputStream fos = new FileOutputStream(output);

Convert TIF to JPG 110


Real's HowTo PDF version

JPEGImageEncoder jpeg = JPEGCodec.createJPEGEncoder(fos);


jpeg.encode(op.getData());
fos.close();
}

public static void main(String[] args) throws Exception {


TiffUtils.TiffToJpg("c:/users/public/temp/test.tif",
"c:/users/public/temp/test.jpg");
}
}

Need some TIFFs for testing ? Just ask Google!

Written and compiled Réal Gagnon ©2015 [email protected]


http://www.rgagnon.com

Convert TIF to JPG 111


Date and Time
java-date

Have year on 4 digits from a Date object


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0096.html

You need to add 1900 to it to get the 4 digit year.

int year = myDate.getYear() + 1900;

The getYear() method returns the number of years elapsed after the year 1900. So for year 2000,
mydate.getYear() will return 100. So 100 + 1900 = 2000.

Get the current Date and Time


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0106.html

import java.util.Calendar;
import java.text.SimpleDateFormat;

public class DateUtils {


public static final String DATE_FORMAT_NOW = "yyyy-MM-dd HH:mm:ss";

public static String now() {


Calendar cal = Calendar.getInstance();
SimpleDateFormat sdf = new SimpleDateFormat(DATE_FORMAT_NOW);
return sdf.format(cal.getTime());

public static void main(String arg[]) {


System.out.println("Now : " + DateUtils.now());
}
}

Here some formatting possibilities available through the SimpleDateFormat class.

import java.util.Calendar;
import java.text.SimpleDateFormat;

Date and Time 112


Real's HowTo PDF version

public class DateUtils {

public static String now(String dateFormat) {


Calendar cal = Calendar.getInstance();
SimpleDateFormat sdf = new SimpleDateFormat(dateFormat);
return sdf.format(cal.getTime());

public static void main(String arg[]) {


System.out.println(DateUtils.now("dd MMMMM yyyy"));
System.out.println(DateUtils.now("yyyyMMdd"));
System.out.println(DateUtils.now("dd.MM.yy"));
System.out.println(DateUtils.now("MM/dd/yy"));
System.out.println(DateUtils.now("yyyy.MM.dd G 'at' hh:mm:ss z"));
System.out.println(DateUtils.now("EEE, MMM d, ''yy"));
System.out.println(DateUtils.now("h:mm a"));
System.out.println(DateUtils.now("H:mm:ss:SSS"));
System.out.println(DateUtils.now("K:mm a,z"));
System.out.println(DateUtils.now("yyyy.MMMMM.dd GGG hh:mm aaa"));
}
}

Thanks to T. Guirado for the idea.

Compute days between 2 dates


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0097.html

One technique is to compute by hand the number of milliseconds between two dates and then convert the
result in days.

import java.util.*;

public class DateUtils {


private DateUtils() { }

static final long ONE_HOUR = 60 * 60 * 1000L;


public static long daysBetween(Date d1, Date d2){
return ( (d2.getTime() - d1.getTime() + ONE_HOUR) /
(ONE_HOUR * 24));
}

/*
testing
*/
public static void main(String[] args) {

Get the current Date and Time 113


Real's HowTo PDF version

java.text.SimpleDateFormat sdf =
new java.text.SimpleDateFormat("yyyyMMdd");
Calendar first = Calendar.getInstance();
first.set(2008, Calendar.AUGUST, 1);
Calendar second = Calendar.getInstance();

System.out.println
(daysBetween(first.getTime(),second.getTime())
+ " day(s) between "
+ sdf.format(first.getTime()) + " and "
+ sdf.format(second.getTime()));
/*
* output :
* 21 day(s) between 20080801 and 20080822
*/
}
}

NOTE: The daysBetween() method works only on Dates set at midnight. One hour (known as the "fudge" factor) is added to the 2 Dates passed as parameters
to take in account the possible DLS (Day Light Saving) one hour missing.

Another way would be to compute the julian day number of both dates and then do the substraction. See this
HowTo. Thanks to P. Hill for the tip.

The package java.util.concurrent.TimeUnit; provides a class to make conversion between milliseconds and
days easier.
import java.util.*;
import java.util.concurrent.TimeUnit;

public class DateUtils {


private DateUtils() { }

public static long getDifference(Calendar a, Calendar b, TimeUnit units) {


return
units.convert(b.getTimeInMillis() - a.getTimeInMillis(), TimeUnit.MILLISECONDS);
}

/*
testing
*/
public static void main(String[] args) {
java.text.SimpleDateFormat sdf =
new java.text.SimpleDateFormat("yyyyMMdd");
Calendar augustfirst2008 = Calendar.getInstance();
augustfirst2008.set(2008, Calendar.AUGUST, 1); // 2008-08-01
Calendar today = Calendar.getInstance(); // today

System.out.println
(getDifference(augustfirst2008,today,TimeUnit.DAYS)
+ " day(s) between "
+ sdf.format(augustfirst2008.getTime()) + " and "
+ sdf.format(today.getTime()));
}

Compute days between 2 dates 114


Real's HowTo PDF version

/*
* output :
* 921 day(s) between 20080801 and 20110208
*/
}

Get the number of days in a month


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0098.html

public static int daysInMonth(GregorianCalendar c) {


int [] daysInMonths = {31,28,31,30,31,30,31,31,30,31,30,31};
daysInMonths[1] += c.isLeapYear(c.get(GregorianCalendar.YEAR)) ? 1 : 0;
return daysInMonths[c.get(GregorianCalendar.MONTH)];
}

Actually, the Calendar class provides a method to that very simply. For a given Calendar or
GregorianCalendar object :

calObject.getActualMaximum(calobject.DAY_OF_MONTH)

In the Java API documentation there is a note saying that The version (getActualMaximum()) of this function
on Calendar uses an iterative algorithm to determine the actual maximum value for the field. There is almost
always a more efficient way to accomplish this (in most cases, you can simply return getMaximum()).
GregorianCalendar overrides this function with a more efficient implementation. So it looks like it's a lot
more efficient to call getActualMaximum from a GregorianCalendar object than a Calendar object. (Thanks to P.
Harris for the tip)

gregCalObject.getActualMaximum(gregCalObject.DAY_OF_MONTH)

Validate a date
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0099.html

Using DateFormat

import java.text.*;

public class DateUtils {


public static boolean isValidDateStr(String date) {
try {
DateFormat df =

Get the number of days in a month 115


Real's HowTo PDF version

DateFormat.getDateInstance
(DateFormat.SHORT); // YYYY-MM-DD
df.setLenient(false); // this is important!
df.parse(date);
}
catch (ParseException e) {
return false;
}
catch (IllegalArgumentException e) {
return false;
}
return true;
}

public static void main(String[] args) {


System.out.println(" 1900-12-13 valid ? "
+ DateUtils.isValidDateStr("1900-12-13"));

// "1990-12/13" throws a ParseException


System.out.println(" 1900-12/13 valid ? "
+ DateUtils.isValidDateStr("1900-12/13"));
// "1990-13-12" throws a IllegalArgumentException
System.out.println(" 1900-13-12 valid ? "
+ DateUtils.isValidDateStr("1900-13-12"));
/*
* output :
* 1900-12-13 valid ? true
* 1900-12/13 valid ? false
* 1900-13-12 valid ? false
*/
}
}

Using SimpleDateFormat

package com.rgagnon.howto;

import java.text.*;

public class DateUtils {


public static boolean isValidDateStr(String date, String format) {
try {
SimpleDateFormat sdf = new SimpleDateFormat(format);
sdf.setLenient(false);
sdf.parse(date);
}
catch (ParseException e) {
return false;
}
catch (IllegalArgumentException e) {
return false;
}
return true;
}

Validate a date 116


Real's HowTo PDF version

public static void main(String[] args) {


System.out.println(" 1900-12-13 valid ? "
+ DateUtils.isValidDateStr("1900-12-13","yyyy-MM-dd"));

// "1990-12/13" throws a ParseException


System.out.println(" 1900-12/13 valid ? "
+ DateUtils.isValidDateStr("1900-12/13","yyyy-MM-dd"));
// "1990-13-12" throws a IllegalArgumentException
System.out.println(" 1900-13-12 valid ? "
+ DateUtils.isValidDateStr("1900-13-12","yyyy-MM-dd"));
/*
* output :
* 1900-12-13 valid ? true
* 1900-12/13 valid ? false
* 1900-13-12 valid ? false
*/
}
}

Using GregorianCalendar

import java.util.*;

public class jtest {


public static void main(String args[]) {
try {
GregorianCalendar gc = new GregorianCalendar();
gc.setLenient(false); // must do this
gc.set(GregorianCalendar.YEAR, 2003);
gc.set(GregorianCalendar.MONTH, 42);// invalid month
gc.set(GregorianCalendar.DATE, 1);

gc.getTime(); // exception thrown here


}
catch (Exception e) {
e.printStackTrace();
}
}
}

Determine the day of the week


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0100.html

For the day of the week for today :

GregorianCalendar newCal = new GregorianCalendar( );


int day = newCal.get( Calendar.DAY_OF_WEEK );

Validate a date 117


Real's HowTo PDF version

For the day of the week for any date :

Calendar newCal = new GregorianCalendar();


newCal.set(1997, 2, 1, 0, 0, 0);
// BUG fix in Calendar class!
newCal.setTime(newCal.getTime());
int day = newCal.get(Calendar.DAY_OF_WEEK);
/*
also available :
newCal.get( Calendar.DAY_OF_MONTH )
newCal.get( Calendar.DAY_OF_WEEK_IN_MONTH )
newCal.get( Calendar.DAY_OF_YEAR )
newCal.get( Calendar.DATE )
*/

Add/Substract Day/Month/Year to a Date


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0101.html

add() and roll() are used to add or substract values to a Calendar object.

You specify which Calendar field is to be affected by the operation (Calendar.YEAR, Calendar.MONTH,
Calendar.DATE).

add() adds or substracts values to the specified Calendar field, the next larger field is modified when the result
makes the Calendar "rolls over".

import java.util.Calendar;
import java.text.SimpleDateFormat;

public class Test {


public static void main(String[] args) throws Exception {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Calendar c1 = Calendar.getInstance();
c1.set(1999, 0 , 20); // 1999 jan 20
System.out.println("Date is : " + sdf.format(c1.getTime()));
c1.add(Calendar.DATE,20); // or Calendar.DAY_OF_MONTH which is a synonym
System.out.println("Date + 20 days is : " + sdf.format(c1.getTime()));
/*
* output :
* Date is : 1999-01-20
* Date + 20 days is : 1999-02-09
*/
}
}

To substract, simply use a negative argument.

Determine the day of the week 118


Real's HowTo PDF version

roll() does the same thing except you specify if you want to roll up (add 1) or roll down (substract 1) to the
specified Calendar field. The operation only affects the specified field while add() adjusts other Calendar
fields.

See the following example, roll() makes january rolls to december in the same year while add() substract the
YEAR field for the correct result.

import java.util.Calendar;
import java.text.SimpleDateFormat;

public class Test {


public static void main(String[] args) throws Exception {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Calendar c1 = Calendar.getInstance();
c1.set(1999, 0 , 20); // 1999 jan 20
System.out.println("Date is : " + sdf.format(c1.getTime()));
c1.roll(Calendar.MONTH, false); // roll down, substract 1 month
System.out.println ("Date roll down 1 month : "
+ sdf.format(c1.getTime()));

c1.set(1999, 0 , 20); // 1999 jan 20


System.out.println("Date is : " + sdf.format(c1.getTime()));
c1.add(Calendar.MONTH, -1); // substract 1 month
System.out.println
("Date minus 1 month : "
+ sdf.format(c1.getTime()));
/*
* output :
* Date is : 1999-01-20
* Date roll down 1 month : 1999-12-20
* Date is : 1999-01-20
* Date minus 1 month : 1998-12-20
*/
}
}

Get the correct TimeZone on DateFormat


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0102.html

There is a bug in the DateFormat/SimpleDateFormat classes. We must set the TimeZone manually.

System.out.println("Good TimeZone from Calendar : " +


Calendar.getInstance().getTimeZone().getID());
DateFormat df = DateFormat.getDateInstance();
System.out.println("Bad TimeZone from DateFormat : " +
df.getTimeZone().getID());
// fix the TimeZone
df.setCalendar(Calendar.getInstance());

Add/Substract Day/Month/Year to a Date 119


Real's HowTo PDF version

System.out.println("Good TimeZone from DateFormat : " +


df.getTimeZone.getID());

Simply format a date as "YYYYMMDD"


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0103.html

The format "YYYYMMDD" can be useful when sorting records or comparing 2 dates.

public static String getStrDate(GregorianCalendar c) {


int m = c.get(GregorianCalendar.MONTH) + 1;
int d = c.get(GregorianCalendar.DATE);
String mm = Integer.toString(m);
String dd = Integer.toString(d);
return "" + c.get(GregorianCalendar.YEAR) + (m < 10 ? "0" + mm : mm) +
(d < 10 ? "0" + dd : dd);
}

Thanks to Vladimir Garmaev for the bug fix

Or you can use the SimpleDateFormat from the java.text package.

import java.util.Calendar;
import java.text.SimpleDateFormat;

public class TestDate {


public static void main(String args[]){
String DATE_FORMAT = "yyyyMMdd";
SimpleDateFormat sdf =
new SimpleDateFormat(DATE_FORMAT);
Calendar c1 = Calendar.getInstance(); // today
System.out.println("Today is " + sdf.format(c1.getTime()));
}
}

Compare 2 dates
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0104.html

import java.util.*;
import java.util.*;
import java.text.*;

public class TestDate {

Get the correct TimeZone on DateFormat 120


Real's HowTo PDF version

public static void main(String args[]){


String DATE_FORMAT = "yyyy-MM-dd";
java.text.SimpleDateFormat sdf =
new java.text.SimpleDateFormat(DATE_FORMAT);
Calendar c1 = Calendar.getInstance();
Calendar c2 = Calendar.getInstance();
// remember months are zero-based : 0 jan 1 feb ...
c1.set(1999, 11 , 31);
c2.set(1999, 0 , 30);

System.out.print(sdf.format(c1.getTime()));

if (c1.before(c2)) {
System.out.print(" is before ");
}
if (c1.after(c2)) {
System.out.print(" is after ");
}
if (c1.equals(c2)) {
System.out.print(" same as ");
}
System.out.println(sdf.format(c2.getTime()));
}
}

Parse a String to obtain a Date/GregorianCalendar object


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0105.html

import java.util.Date;
import java.util.Locale;
import java.util.Calendar;
import java.text.SimpleDateFormat;

public class DateUtils {

public static Calendar parseTimestamp(String timestamp)


throws Exception {
/*
** we specify Locale.US since months are in english
*/
SimpleDateFormat sdf = new SimpleDateFormat
("dd-MMM-yyyy HH:mm:ss", Locale.US);
Date d = sdf.parse(timestamp);
Calendar cal = Calendar.getInstance();
cal.setTime(d);
return cal;
}

Compare 2 dates 121


Real's HowTo PDF version

public static void main (String a[]) throws Exception{


String timestampToParse = "24-Feb-1998 17:39:35";
System.out.println("Timestamp : " + timestampToParse);

SimpleDateFormat sdf =
new java.text.SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
System.out.println("Calendar : "
+ sdf.format(parseTimestamp(timestampToParse).getTime()));
/*
output :
Timestamp : 24-Feb-1998 17:39:35
Calendar : 1998-02-24 17:39:35
*/
}

Use System time to generate unique ID


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0385.html

Since the granulaty of a PC can be as high as 55ms (down to 10ms), you can't use the System time to generate
a unique ID because of the risk of getting duplicated IDs. This can be solved by using the following technique
to make sure that the number returned is unique (in a single JVM).

public class UniqueID {


static long current= System.currentTimeMillis();
static public synchronized long get(){
return current++;
}
}

See also this HowTo

Get the day name


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0403.html

import java.util.*;
import java.text.SimpleDateFormat;
import java.text.DateFormat;

public class GetDayName {

Parse a String to obtain a Date/GregorianCalendar object 122


Real's HowTo PDF version

public static void main(String[] args) {


Date date1 =
(new GregorianCalendar
(1989, Calendar.OCTOBER, 17)).getTime();
Date date2 = new Date();
System.out.println
("1989-10-17 was a " + sayDayName(date1));
System.out.println("Today is a " + sayDayName(date2));
}

public static String sayDayName(Date d) {


DateFormat f = new SimpleDateFormat("EEEE");
try {
return f.format(d);
}
catch(Exception e) {
e.printStackTrace();
return "";
}
}
}

An alternate way :

import java.util.Calendar;
import java.text.SimpleDateFormat;
import java.text.DateFormat;
import java.text.DateFormatSymbols;

public class GetDayName {

public static void main(String[] args) {


String dayNames[] = new DateFormatSymbols().getWeekdays();
Calendar date2 = Calendar.getInstance();
System.out.println("Today is a "
+ dayNames[date2.get(Calendar.DAY_OF_WEEK)]);
}
}

Find the date format pattern


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0413.html

import java.text.*;
import java.util.*;
public class Dtest {
public static void main(String args[]) {

Get the day name 123


Real's HowTo PDF version

SimpleDateFormat df = (SimpleDateFormat)
DateFormat.getDateInstance(DateFormat.SHORT);
System.out.println("The short date format is " + df.toPattern());
Locale loc = Locale.ITALY;
df = (SimpleDateFormat)
DateFormat.getDateInstance(DateFormat.SHORT, loc);
System.out.println("The short date format is " + df.toPattern());
}
}

Get a julian date


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0506.html

A Julian date is the number of elapsed days since the beginning of a cycle of 7,980 years invented by Joseph
Scaliger in 1583. The purpose of the system is to make it easy to compute an integer (whole number)
difference between one calendar date and another calendar date.

The starting point for the first Julian cycle began on January 1, 4713 B.C. and will end on January 22, 3268
(3268-01-22 G). The following day will begin the first day of the second Julian date period (or 7,980 year
cycle).

import java.util.Calendar;
public class JulianDate {
/**
* Returns the Julian day number that begins at noon of
* this day, Positive year signifies A.D., negative year B.C.
* Remember that the year after 1 B.C. was 1 A.D.
*
* ref :
* Numerical Recipes in C, 2nd ed., Cambridge University Press 1992
*/
// Gregorian Calendar adopted Oct. 15, 1582 (2299161)
public static int JGREG= 15 + 31*(10+12*1582);
public static double HALFSECOND = 0.5;

public static double toJulian(int[] ymd) {


int year=ymd[0];
int month=ymd[1]; // jan=1, feb=2,...
int day=ymd[2];
int julianYear = year;
if (year < 0) julianYear++;
int julianMonth = month;
if (month > 2) {
julianMonth++;
}
else {
julianYear--;
julianMonth += 13;

Find the date format pattern 124


Real's HowTo PDF version

double julian = (java.lang.Math.floor(365.25 * julianYear)


+ java.lang.Math.floor(30.6001*julianMonth) + day + 1720995.0);
if (day + 31 * (month + 12 * year) >= JGREG) {
// change over to Gregorian calendar
int ja = (int)(0.01 * julianYear);
julian += 2 - ja + (0.25 * ja);
}
return java.lang.Math.floor(julian);
}

/**
* Converts a Julian day to a calendar date
* ref :
* Numerical Recipes in C, 2nd ed., Cambridge University Press 1992
*/
public static int[] fromJulian(double injulian) {
int jalpha,ja,jb,jc,jd,je,year,month,day;
double julian = injulian + HALFSECOND / 86400.0;
ja = (int) julian
if (ja>= JGREG) {
jalpha = (int) (((ja - 1867216) - 0.25) / 36524.25);
ja = ja + 1 + jalpha - jalpha / 4;
}

jb = ja + 1524;
jc = (int) (6680.0 + ((jb - 2439870) - 122.1) / 365.25);
jd = 365 * jc + jc / 4;
je = (int) ((jb - jd) / 30.6001);
day = jb - jd - (int) (30.6001 * je);
month = je - 1;
if (month > 12) month = month - 12;
year = jc - 4715;
if (month > 2) year--;
if (year <= 0) year--;

return new int[] {year, month, day};


}

public static void main(String args[]) {


// FIRST TEST reference point
System.out.println("Julian date for May 23, 1968 : "
+ toJulian( new int[] {1968, 5, 23 } ));
// output : 2440000
int results[] = fromJulian(toJulian(new int[] {1968, 5, 23 }));
System.out.println
("... back to calendar : " + results[0] + " "
+ results[1] + " " + results[2]);

// SECOND TEST today


Calendar today = Calendar.getInstance();
double todayJulian = toJulian
(new int[]{today.get(Calendar.YEAR), today.get(Calendar.MONTH)+1,

Get a julian date 125


Real's HowTo PDF version

today.get(Calendar.DATE)});
System.out.println("Julian date for today : " + todayJulian);
results = fromJulian(todayJulian);
System.out.println
("... back to calendar : " + results[0] + " " + results[1]
+ " " + results[2]);

// THIRD TEST
double date1 = toJulian(new int[]{2005,1,1});
double date2 = toJulian(new int[]{2005,1,31});
System.out.println("Between 2005-01-01 and 2005-01-31 : "
+ (date2 - date1) + " days");

/*
expected output :
Julian date for May 23, 1968 : 2440000.0
... back to calendar 1968 5 23
Julian date for today : 2453487.0
... back to calendar 2005 4 26
Between 2005-01-01 and 2005-01-31 : 30.0 days
*/
}
}

There is a lot of variation around the idea of a "Julian date". You can have the Modified Julian Date (JD) or
the Truncated Julian Date (TJD). The main difference is the starting for counting the days.

Before Y2K, many applications (especially mainframe systems) were storing dates in a format called "the
Julian format". This format is a 5 digit number, consisting of a 2 digit year and a 3 digit day-of-year number.
For example, 17-July-1998 is stored as 98221, since 17-July is the 221th day of the year. This format is not
really useful since Y2K! The main reason for using the 5-digits Julian date was to save disk space and still
have a format easy to use to handle. dates.

A variation of this idea is to used the first four digits for the year and 3 digits for day-of-year, 17-July-1998
will be represented by 1998221.

This is a very simple format which can be manipulated easily from Java.

import java.util.Calendar;
import java.util.Date;
import java.text.ParseException;
import java.text.SimpleDateFormat;

public class DateUtils {


private DateUtils() { }

public static Date getDateFromJulian7(String julianDate)


throws ParseException
{
return new SimpleDateFormat("yyyyD").parse(julianDate);
}

Get a julian date 126


Real's HowTo PDF version

public static String getJulian7FromDate(Date date) {


StringBuilder sb = new StringBuilder();
Calendar cal = Calendar.getInstance();
cal.setTime(date);

return sb.append(cal.get(Calendar.YEAR))
.append(String.format("%03d", cal.get(Calendar.DAY_OF_YEAR)))
.toString();
}

public static void main(String[] args) throws Exception {


String test = "1998221";
Date d = DateUtils.getDateFromJulian7(test);
System.out.println(d);
System.out.println(DateUtils.getJulian7FromDate(d));

/*
* output :
* Sun Aug 09 00:00:00 EDT 1998
* 1998221
*/
}
}

Calculate the age


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0547.html

import java.util.GregorianCalendar;
import java.util.Calendar;

public class CalcAge {

public static void main(String [] args) {


// remember ... months are 0-based : jan=0 feb=1 ...
System.out.println
("1962-11-11 : " + age(1962,10,11));
System.out.println
("1999-12-03 : " + age(1999,11,3));
}

private static int age(int y, int m, int d) {


Calendar cal = new GregorianCalendar(y, m, d);
Calendar now = new GregorianCalendar();
int res = now.get(Calendar.YEAR) - cal.get(Calendar.YEAR);
if((cal.get(Calendar.MONTH) > now.get(Calendar.MONTH))
|| (cal.get(Calendar.MONTH) == now.get(Calendar.MONTH)

Calculate the age 127


Real's HowTo PDF version

&& cal.get(Calendar.DAY_OF_MONTH) > now.get(Calendar.DAY_OF_MONTH)))


{
res--;
}
return res;
}
}

Format a duration in milliseconds into a human-readable format


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0585.html

Given a time in ms, this HowTo will output the long form "<w> days, <x> hours, <y> minutes and (z)
seconds" and the short form "<dd:>hh:mm:ss".

public class TimeUtils {

public final static long ONE_SECOND = 1000;


public final static long SECONDS = 60;

public final static long ONE_MINUTE = ONE_SECOND * 60;


public final static long MINUTES = 60;

public final static long ONE_HOUR = ONE_MINUTE * 60;


public final static long HOURS = 24;

public final static long ONE_DAY = ONE_HOUR * 24;

private TimeUtils() {
}

/**
* converts time (in milliseconds) to human-readable format
* "<w> days, <x> hours, <y> minutes and (z) seconds"
*/
public static String millisToLongDHMS(long duration) {
StringBuffer res = new StringBuffer();
long temp = 0;
if (duration >= ONE_SECOND) {
temp = duration / ONE_DAY;
if (temp > 0) {
duration -= temp * ONE_DAY;
res.append(temp).append(" day").append(temp > 1 ? "s" : "")
.append(duration >= ONE_MINUTE ? ", " : "");
}

temp = duration / ONE_HOUR;


if (temp > 0) {
duration -= temp * ONE_HOUR;
res.append(temp).append(" hour").append(temp > 1 ? "s" : "")

Format a duration in milliseconds into a human-readable format 128


Real's HowTo PDF version

.append(duration >= ONE_MINUTE ? ", " : "");


}

temp = duration / ONE_MINUTE;


if (temp > 0) {
duration -= temp * ONE_MINUTE;
res.append(temp).append(" minute").append(temp > 1 ? "s" : "");
}

if (!res.toString().equals("") && duration >= ONE_SECOND) {


res.append(" and ");
}

temp = duration / ONE_SECOND;


if (temp > 0) {
res.append(temp).append(" second").append(temp > 1 ? "s" : "");
}
return res.toString();
} else {
return "0 second";
}
}

/**
* converts time (in milliseconds) to human-readable format
* "<dd:>hh:mm:ss"
*/
public static String millisToShortDHMS(long duration) {
String res = "";
duration /= ONE_SECOND;
int seconds = (int) (duration % SECONDS);
duration /= SECONDS;
int minutes = (int) (duration % MINUTES);
duration /= MINUTES;
int hours = (int) (duration % HOURS);
int days = (int) (duration / HOURS);
if (days == 0) {
res = String.format("%02d:%02d:%02d", hours, minutes, seconds);
} else {
res = String.format("%dd%02d:%02d:%02d", days, hours, minutes, seconds);
}
return res;
}

public static void main(String args[]) {


System.out.println(millisToLongDHMS(123));
System.out.println(millisToLongDHMS((5 * ONE_SECOND) + 123));
System.out.println(millisToLongDHMS(ONE_DAY + ONE_HOUR));
System.out.println(millisToLongDHMS(ONE_DAY + 2 * ONE_SECOND));
System.out.println(millisToLongDHMS(ONE_DAY + ONE_HOUR + (2 * ONE_MINUTE)));
System.out.println(millisToLongDHMS((4 * ONE_DAY) + (3 * ONE_HOUR)
+ (2 * ONE_MINUTE) + ONE_SECOND));
System.out.println(millisToLongDHMS((5 * ONE_DAY) + (4 * ONE_HOUR)
+ ONE_MINUTE + (23 * ONE_SECOND) + 123));

Format a duration in milliseconds into a human-readable format 129


Real's HowTo PDF version

System.out.println(millisToLongDHMS(42 * ONE_DAY));
/*
output :
0 second
5 seconds
1 day, 1 hour
1 day and 2 seconds
1 day, 1 hour, 2 minutes
4 days, 3 hours, 2 minutes and 1 second
5 days, 4 hours, 1 minute and 23 seconds
42 days
*/
System.out.println(millisToShortDHMS(123));
System.out.println(millisToShortDHMS((5 * ONE_SECOND) + 123));
System.out.println(millisToShortDHMS(ONE_DAY + ONE_HOUR));
System.out.println(millisToShortDHMS(ONE_DAY + 2 * ONE_SECOND));
System.out
.println(millisToShortDHMS(ONE_DAY + ONE_HOUR + (2 * ONE_MINUTE)));
System.out.println(millisToShortDHMS((4 * ONE_DAY) + (3 * ONE_HOUR)
+ (2 * ONE_MINUTE) + ONE_SECOND));
System.out.println(millisToShortDHMS((5 * ONE_DAY) + (4 * ONE_HOUR)
+ ONE_MINUTE + (23 * ONE_SECOND) + 123));
System.out.println(millisToShortDHMS(42 * ONE_DAY));
/*
output :
00:00:00
00:00:05
1d01:00:00
1d00:00:02
1d01:02:00
4d03:02:01
5d04:01:23
42d00:00:00

*/
}
}

Using java.util.concurrent.TimeUnit

import java.util.concurrent.TimeUnit;
...

/**
* converts time (in milliseconds) to human-readable format
* "<dd:>hh:mm:ss"
*/
public static String millisToShortDHMS(long duration) {
String res = "";
long days = TimeUnit.MILLISECONDS.toDays(duration);
long hours = TimeUnit.MILLISECONDS.toHours(duration)
- TimeUnit.DAYS.toHours(TimeUnit.MILLISECONDS.toDays(duration));
long minutes = TimeUnit.MILLISECONDS.toMinutes(duration)

Format a duration in milliseconds into a human-readable format 130


Real's HowTo PDF version

- TimeUnit.HOURS.toMinutes(TimeUnit.MILLISECONDS.toHours(duration));
long seconds = TimeUnit.MILLISECONDS.toSeconds(duration)
- TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(duration));
if (days == 0) {
res = String.format("%02d:%02d:%02d", hours, minutes, seconds);
}
else {
res = String.format("%dd%02d:%02d:%02d", days, hours, minutes, seconds);
}
return res;
}

Get the atomic time


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0589.html

We connect to a publicly accessible time server on the internet and parse the result.

List of available time servers : http://tf.nist.gov/tf-cgi/servers.cgi

NOTE : All users should ensure that their software NEVER queries a server more frequently than once every
4 seconds. Systems that exceed this rate will be refused service. In extreme cases, systems that exceed this
limit may be considered as attempting a denial-of-service attack.

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.TimeZone;

public final class DateUtils {


// NIST, Boulder, Colorado (time-a.timefreq.bldrdoc.gov)
// public static final String ATOMICTIME_SERVER="132.163.4.101";
// NIST, Gaithersburg, Maryland (time-a.nist.gov)
// public static final String ATOMICTIME_SERVER="129.6.15.28";
// NIST, Gaithersburg, Maryland (time-c.nist.gov)
public static final String ATOMICTIME_SERVER="129.6.15.30";
public static final int ATOMICTIME_PORT = 13;

public final static GregorianCalendar getAtomicTime() throws IOException{


BufferedReader in = null;
Socket conn = null;

try {
conn = new Socket(ATOMICTIME_SERVER, ATOMICTIME_PORT);

Get the atomic time 131


Real's HowTo PDF version

in = new BufferedReader
(new InputStreamReader(conn.getInputStream()));

String atomicTime;
while (true) {
if ( (atomicTime = in.readLine()).indexOf("*") > -1) {
break;
}
}
System.out.println("DEBUG 1 : " + atomicTime);
String[] fields = atomicTime.split(" ");
GregorianCalendar calendar = new GregorianCalendar();

String[] date = fields[1].split("-");


calendar.set(Calendar.YEAR, 2000 + Integer.parseInt(date[0]));
calendar.set(Calendar.MONTH, Integer.parseInt(date[1])-1);
calendar.set(Calendar.DATE, Integer.parseInt(date[2]));

// deals with the timezone and the daylight-saving-time (you may need to adjust this)
// here i'm using "EST" for Eastern Standart Time (to support Daylight Saving Time)
TimeZone tz = TimeZone.getTimeZone("EST"); // or .getDefault()
int gmt = (tz.getRawOffset() + tz.getDSTSavings()) / 3600000;
System.out.println("DEBUG 2 : " + gmt);

String[] time = fields[2].split(":");


calendar.set(Calendar.HOUR_OF_DAY, Integer.parseInt(time[0]) + gmt);
calendar.set(Calendar.MINUTE, Integer.parseInt(time[1]));
calendar.set(Calendar.SECOND, Integer.parseInt(time[2]));
return calendar;
}
catch (IOException e){
throw e;
}
finally {
if (in != null) { in.close(); }
if (conn != null) { conn.close(); }
}
}

public static void main(String args[]) throws IOException {


SimpleDateFormat sdf =
new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
System.out.println("Atomic time : " +
sdf.format(DateUtils.getAtomicTime().getTime()));
}

/*
ref : http://www.bldrdoc.gov/doc-tour/atomic_clock.html

49825 95-04-18 22:24:11 50 0 0 50.0 UTC(NIST) *

| | | | | | | | |

Get the atomic time 132


Real's HowTo PDF version

These are the last + | | || | | | |


five digits of the | | || | | | |
Modified Julian Date | | || | | | |
| | || | | | |
Year, Month and Day <----+ | || | | | |
| || | | | |
Hour, minute, and second of the <-+ || | | | |
current UTC at Greenwich. || | | | |
|| | | | |
DST - Daylight Savings Time code <------+ | | | | |
00 means standard time(ST), 50 means DST | | | | |
99 to 51 = Now on ST, goto DST when local | | | | |
time is 2:00am, and the count is 51. | | | | |
49 to 01 = Now on DST, goto ST when local | | | | |
time is 2:00am, and the count is 01. | | | | |
| | | | |
Leap second flag is set to "1" when <-----+ | | | |
a leap second will be added on the last | | | |
day of the current UTC month. A value of | | | |
"2" indicates the removal of a leap second. | | | |
| | | |
Health Flag. The normal value of this | <-+
| |
flag is 0. Positive values mean there may | | |
be an error with the transmitted time. | | |
| | |
The number of milliseconds ACTS is advancing <-+ | |
the time stamp, to account for network lag. | |
| |
Coordinated Universal Time from the National <--------+ |
Institute of Standards & Technology. |
|
The instant the "*" appears, is the exact time. <------------+
*/
}

// thanks to TrueJavaProgrammer for the idea!

It's not possible to set your local computer clock in pure Java.

You need to use an external utility provided by the OS or call a JNI routine, see this HowTo.

Get a date interval


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0611.html

This HowTo computes a date interval based on the current date or given reference date. The returned interval
can be the previous week ou the previous month relative to the given reference date.

import java.text.*;

Get a date interval 133


Real's HowTo PDF version

import java.util.*;

public class DateUtils {

public enum IntervalType { Month, Week }

private DateUtils() { }

public static Calendar[] getDateIntervals(IntervalType type, Calendar reference) {


if (reference == null) {
reference = Calendar.getInstance();
}
Calendar startDate = (Calendar)reference.clone();
Calendar endDate = (Calendar)reference.clone();

if (type == IntervalType.Month) {
// first date of the month
startDate.set(Calendar.DATE, 1);
// previous month
startDate.add(Calendar.MONTH, -1);

// first date of the month


endDate.set(Calendar.DATE, 1);
// previous month, last date
endDate.add(Calendar.DATE, -1);
}
else {
// previous week by convention (monday ... sunday)
// you will have to adjust this a bit if you want
// sunday to be considered as the first day of the week.
// start date : decrement until first sunday then
// down to monday
int dayOfWeek = startDate.get(Calendar.DAY_OF_WEEK);
while (dayOfWeek != Calendar.SUNDAY) {
startDate.add(Calendar.DATE, -1);
dayOfWeek = startDate.get(Calendar.DAY_OF_WEEK);
}
while (dayOfWeek != Calendar.MONDAY) {
startDate.add(Calendar.DATE, -1);
dayOfWeek = startDate.get(Calendar.DAY_OF_WEEK);
}

// end date , decrement until the first sunday


dayOfWeek = endDate.get(Calendar.DAY_OF_WEEK);
while (dayOfWeek != Calendar.SUNDAY) {
endDate.add(Calendar.DATE, -1);
dayOfWeek = endDate.get(Calendar.DAY_OF_WEEK);
}
}
return new Calendar[] { startDate, endDate };
}

public static void main(String[] args) {


try {

Get a date interval 134


Real's HowTo PDF version

SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");

System.out.println("** previous month (relative today)");


Calendar [] results = DateUtils.getDateIntervals(IntervalType.Month, null);
System.out.println(sdf.format(results[0].getTime()));
System.out.println(sdf.format(results[1].getTime()));

System.out.println("** previous week (relative today)");


results = DateUtils.getDateIntervals(IntervalType.Week, null);
System.out.println(sdf.format(results[0].getTime()));
System.out.println(sdf.format(results[1].getTime()));

System.out.println("** previous month (relative jan 1, 2007)");


results = DateUtils.getDateIntervals(IntervalType.Month,
new GregorianCalendar(2007, 00, 1));
System.out.println(sdf.format(results[0].getTime()));
System.out.println(sdf.format(results[1].getTime()));

System.out.println("** previous week (relative jan 1, 2007)");


results = DateUtils.getDateIntervals(IntervalType.Week,
new GregorianCalendar(2007, 00, 1));
System.out.println(sdf.format(results[0].getTime()));
System.out.println(sdf.format(results[1].getTime()));

}
catch (Exception e) {
e.printStackTrace();
}
}
/*
output :
** previous month (relative today)
2008-06-01
2008-06-30
** previous week (relative today)
2008-06-30
2008-07-06
** previous month (relative jan 1, 2007)
2006-12-01
2006-12-31
** previous week (relative jan 1, 2007)
2006-12-25
2006-12-31
*/
}

Determine if a given hour is between an interval


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0624.html

Determine if a given hour is between an interval 135


Real's HowTo PDF version

import java.util.Calendar;
import java.text.SimpleDateFormat;

public class DateUtils {

// format 24hre ex. 12:12 , 17:15


private static String HOUR_FORMAT = "HH:mm";

private DateUtils() { }

public static String getCurrentHour() {


Calendar cal = Calendar.getInstance();
SimpleDateFormat sdfHour = new SimpleDateFormat(HOUR_FORMAT);
String hour = sdfHour.format(cal.getTime());
return hour;
}

/**
* @param target hour to check
* @param start interval start
* @param end interval end
* @return true true if the given hour is between
*/
public static boolean isHourInInterval(String target, String start, String end) {
return ((target.compareTo(start) >= 0)
&& (target.compareTo(end) <= 0));
}

/**
* @param start interval start
* @param end interval end
* @return true true if the current hour is between
*/
public static boolean isNowInInterval(String start, String end) {
return DateUtils.isHourInInterval
(DateUtils.getCurrentHour(), start, end);
}

// TEST
public static void main (String[] args) {
String now = DateUtils.getCurrentHour();
String start = "14:00";
String end = "14:26";
System. out.println(now + " between " + start + "-" + end + "?");
System. out.println(DateUtils.isHourInInterval(now,start,end));
/*
* output example :
* 21:01 between 14:00-14:26?
* false
*
*/
}
}

Determine if a given hour is between an interval 136


Real's HowTo PDF version

Set the computer clock (JNI)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0285.html

Define the following prototype in the header file

JNIEXPORT void JNICALL Java_JavaHowTo_setSystemTime


(JNIEnv *, jobject, jshort, jshort);

the JNI function

JNIEXPORT void JNICALL Java_JavaHowTo_setSystemTime


(JNIEnv *env, jobject obj, jshort hour, jshort minutes) {

SYSTEMTIME st;

GetLocalTime(&st);
st.wHour = hour;
st.wMinute = minutes;
SetLocalTime(&st);
}

The Java JNI wrapper would be

class JavaHowTo {
public native void setSystemTime( short hour, short minutes);
static {
System.loadLibrary("javahowto");
}
}

And finally, to use it

public class JNIJavaHowTo {


public static void main(String[] args) {
short hour = 10;
short minutes = 21;

// this example will set the system at 10h21 using the Windows API
// SetLocalTime.

JavaHowTo jht = new JavaHowTo();


// set the time at 10h21
jht.setSystemTime(hour, minutes);
}
}

Set the computer clock (JNI) 137


Real's HowTo PDF version

Get unique numerical id based on the system time


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0385.html

Since the granulaty of a PC can be as high as 55ms (down to 10ms), you can't use the System time to generate
a unique ID because of the risk of getting duplicated IDs. This can be solved by using the following technique
to make sure that the number returned is unique (in a single JVM).

public class UniqueID {


static long current= System.currentTimeMillis();
static public synchronized long get(){
return current++;
}
}

See also this HowTo

Get the month (or day) name (localized)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0650.html

import java.text.DateFormatSymbols;
import java.util.Locale;

public class DateUtils {


private DateUtils() { }

public static String getMonthName(int month) {


return getMonthName(month, Locale.getDefault());
}

public static String getMonthName(int month, Locale locale) {


DateFormatSymbols symbols = new DateFormatSymbols(locale);
String[] monthNames = symbols.getMonths();
return monthNames[month - 1];
}

public static String getDayName(int day, Locale locale) {


DateFormatSymbols symbols = new DateFormatSymbols(locale);
String[] dayNames = symbols.getWeekdays();
return dayNames[day];
}

Get unique numerical id based on the system time 138


Real's HowTo PDF version

public static void main(String[] args) {

System.out.println(DateUtils.getMonthName(1));
System.out.println(DateUtils.getMonthName(1, new Locale("it")));

System.out.println
(DateUtils.getDayName(java.util.Calendar.SUNDAY, Locale.getDefault()));

/*
* output :
* january
* gennaio
* sunday
*/
}
}

Detect a leap year


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0654.html

The algorithm to determine is a given year is leap or not (>365 days) is :

if year modulo 400 is 0 then


leap
else if year modulo 100 is 0 then
no_leap
else if year modulo 4 is 0 then
leap
else
no_leap

Three techniques to check if a year is leap or not :

import java.util.Calendar;
import java.util.GregorianCalendar;

public class DateUtils {


private DateUtils() { }

// using GregorianCalendar
public static boolean isLeap0(int year) {
GregorianCalendar cal = new GregorianCalendar();
cal.set(Calendar.YEAR, year);
return cal.isLeapYear(cal.get(Calendar.YEAR));
}

Get the month (or day) name (localized) 139


Real's HowTo PDF version

// using a Calendar
public static boolean isLeap1(int year) {
Calendar cal = Calendar.getInstance();
cal.set(Calendar.YEAR, year);
return cal.getActualMaximum(Calendar.DAY_OF_YEAR) > 365;
}

// directly, maybe faster...


public static boolean isLeap2(int year) {
return ((year % 4 == 0) && (year % 100 != 0)) || (year % 400 == 0);
}

public static void main(String[] args) {


System.out.println("1900 : " + DateUtils.isLeap0(1900));
System.out.println("1996 : " + DateUtils.isLeap0(1996));
System.out.println("2000 : " + DateUtils.isLeap0(2000));
System.out.println("2010 : " + DateUtils.isLeap0(2010));
System.out.println("");
System.out.println("1900 : " + DateUtils.isLeap1(1900));
System.out.println("1996 : " + DateUtils.isLeap1(1996));
System.out.println("2000 : " + DateUtils.isLeap1(2000));
System.out.println("2010 : " + DateUtils.isLeap1(2010));
System.out.println("");
System.out.println("1900 : " + DateUtils.isLeap2(1900));
System.out.println("1998 : " + DateUtils.isLeap2(1996));
System.out.println("2000 : " + DateUtils.isLeap2(2000));
System.out.println("2010 : " + DateUtils.isLeap2(2010));
}
}

Written and compiled Réal Gagnon ©2015 [email protected]


http://www.rgagnon.com

Detect a leap year 140


Environment
java-env

Read environment variables from an application


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0150.html

NOTE: JDK1.5 or better provides a simpler way to achieve this, see this HowTo.

JDK up to 1.4
Start the JVM with the "-D" switch to pass properties to the application and read them with the
System.getProperty() method.

SET myvar=Hello world


SET myothervar=nothing
java -Dmyvar="%myvar%" -Dmyothervar="%myothervar%" myClass

then in myClass

String myvar = System.getProperty("myvar");


String myothervar = System.getProperty("myothervar");

If you don't know in advance, the name of the variable to be passed to the JVM, then there is no 100% Java
way to retrieve them.

One approach (not the easiest one), is to use a JNI call to fetch the variables, see this HowTo.

A more low-tech way, is to launch the appropriate call to the operating system and capture the output. The
following snippet puts all environment variables in a Properties class and display the value the TEMP
variable.
import java.io.*;
import java.util.*;

public class ReadEnv {


public static Properties getEnvVars() throws Throwable {
Process p = null;
Properties envVars = new Properties();
Runtime r = Runtime.getRuntime();
String OS = System.getProperty("os.name").toLowerCase();
// System.out.println(OS);
if (OS.indexOf("windows 9") > -1) {
p = r.exec( "command.com /c set" );

Environment 141
Real's HowTo PDF version

}
else if ( (OS.indexOf("nt") > -1)
|| (OS.indexOf("windows 2000") > -1 )
|| (OS.indexOf("windows xp") > -1) ) {
// thanks to JuanFran for the xp fix!
p = r.exec( "cmd.exe /c set" );
}
else {
// our last hope, we assume Unix (thanks to H. Ware for the fix)
p = r.exec( "env" );
}
BufferedReader br = new BufferedReader
( new InputStreamReader( p.getInputStream() ) );
String line;
while( (line = br.readLine()) != null ) {
int idx = line.indexOf( '=' );
String key = line.substring( 0, idx );
String value = line.substring( idx+1 );
envVars.setProperty( key, value );
// System.out.println( key + " = " + value );
}
return envVars;
}

public static void main(String args[]) {


try {
Properties p = ReadEnv.getEnvVars();
System.out.println("the current value of TEMP is : " +
p.getProperty("TEMP"));
}
catch (Throwable e) {
e.printStackTrace();
}
}
}

thanks to w.rijnders for the w2k fix.

An update from Van Ly :

I found that, on Windows 2003 server, the property value for "os.name" is actually "windows 2003." So either
that has to be added to the bunch of tests or just relax the comparison strings a bit:

else if ( (OS.indexOf("nt") > -1)


|| (OS.indexOf("windows 2000") > -1 )
|| (OS.indexOf("windows 2003") > -1 ) // ok
// but specific to 2003
|| (OS.indexOf("windows xp") > -1) ) {

else if ( (OS.indexOf("nt") > -1)

Read environment variables from an application 142


Real's HowTo PDF version

|| (OS.indexOf("windows 20") > -1 ) // better,


// since no other OS would
// return "windows"
|| (OS.indexOf("windows xp") > -1) ) {

I started with "windows 200" but thought "what the hell" and made it "windows 20" to lengthen its longivity.
You could push it further and use "windows 2," I suppose. The only thing to watch out for is to not overlap
with "windows 9."

On Windows, pre-JDK 1.2 JVM has trouble reading the Output stream directly from the SET command, it
never returns. Here 2 ways to bypass this behaviour.

First, instead of calling directly the SET command, we use a BAT file, after the SET command we print a
known string. Then, in Java, when we read this known string, we exit from loop.

[env.bat]

@set
@echo **end

[java]

...
if (OS.indexOf("windows") > -1) {
p = r.exec( "env.bat" );
}
...

while( (line = br.readLine()) != null ) {


if (line.indexOf("**end")>-1) break;
int idx = line.indexOf( '=' );
String key = line.substring( 0, idx );
String value = line.substring( idx+1 );
hash.put( key, value );
System.out.println( key + " = " + value );
}

The other solution is to send the result of the SET command to file and then read the file from Java.

...
if (OS.indexOf("windows 9") > -1) {
p = r.exec( "command.com /c set > envvar.txt" );
}
else if ( (OS.indexOf("nt") > -1)
|| (OS.indexOf("windows 2000") > -1
|| (OS.indexOf("windows xp") > -1) ) {
// thanks to JuanFran for the xp fix!
p = r.exec( "cmd.exe /c set > envvar.txt" );
}

Read environment variables from an application 143


Real's HowTo PDF version

...

// then read back the file as a Propêrties


Properties p = new Properties();
p.load(new FileInputStream("envvar.txt"));

Thanks to JP Daviau

// UNIX
public Properties getEnvironment() throws java.io.IOException {
Properties env = new Properties();
env.load(Runtime.getRuntime().exec("env").getInputStream());
return env;
}

Properties env = getEnvironment();


String myEnvVar = env.get("MYENV_VAR");

To read only one variable :


// NT version , adaptation for other OS is left as an exercise...
Process p = Runtime.getRuntime().exec("cmd.exe /c echo %MYVAR%");
BufferedReader br = new BufferedReader
( new InputStreamReader( p.getInputStream() ) );
String myvar = br.readLine();
System.out.println(myvar);

Java's System properties contains some useful informations about the environment, for example, the TEMP
and PATH environment variables (on Windows).
public class ShowSome {
public static void main(String args[]){
System.out.println("TEMP : "
+ System.getProperty("java.io.tmpdir"));
System.out.println("PATH : "
+ System.getProperty("java.library.path"));
System.out.println("CLASSPATH : "
+ System.getProperty("java.class.path"));
System.out.println("SYSTEM DIR : " +
System.getProperty("user.home")); // ex. c:\windows on Win9x
System.out.println("CURRENT DIR: "
+ System.getProperty("user.dir"));
}
}

Here some tips from H. Ware about the PATH on different OS.

PATH is not quite the same as library path. In unixes, they are completely different---the libraries typically
have their own directories.

System.out.println("the current value of PATH is: {" +


p.getProperty("PATH")+"}");

Read environment variables from an application 144


Real's HowTo PDF version

System.out.println("LIBPATH: {" +
System.getProperty("java.library.path")+"}");

gives

the current value of PATH is:


{/home/hware/bin:/usr/local/bin:/usr/xpg4/bin:/opt/SUNWspro/bin:
/usr/ucb:/bin:/usr/bin:/home/hware/linux-bin:/usr/openwin/bin/:
/usr/local/games:/usr/ccs/lib/:/usr/new:/usr/sbin/:/sbin/:
/usr/openwin/lib:/usr/X11/bin:/usr/bin/X11/:/usr/local/bin/X11:
/usr/bin/pbmplus:/usr/etc/:/usr/dt/bin/:/usr/lib:
/usr/lib/nis:/usr/share/bin:/usr/share/bin/X11:
/home/hware/work/cdk/main/cdk/../bin:.}
LIBPATH:
{/usr/lib/j2re1.3/lib/i386:/usr/lib/j2re1.3/lib/i386/native_threads:
/usr/lib/j2re1.3/lib/i386/client:/usr/lib/j2sdk1.3/lib/i386:/usr/lib:/lib}

on my linux workstation. (java added all those except /lib and /usr/lib). But these two lines aren't the same on
window either:

This system is windows nt

the current value of PATH is:


{d:\OrbixWeb3.2\bin;D:\jdk1.3\bin;c:\depot\cdk\main\cdk\bin;c:\depot\
cdk\main\cdk\..\bin;d:\OrbixWeb3.2\bin;D:\Program
Files\IBM\GSK\lib;H:\pvcs65\VM\win32\bin;c:\cygnus
\cygwin-b20\H-i586-cygwin32\bin;d:\cfn\bin;D:\orant\bin;
C:\WINNT\system32;C:\WINNT;
d:\Program Files\Symantec\pcAnywhere;
C:\Program Files\Executive Software\DiskeeperServer\;}
LIBPATH:
{D:\jdk1.3\bin;.;C:\WINNT\System32;C:\WINNT;D:\jdk1.3\bin;
c:\depot\cdk\main\cdk\bin;c:\depot\cdk\main\cdk\..\bin;
d:\OrbixWeb3.2\bin;D:\Program Files\IBM\GSK\lib;
H:\pvcs65\VM\win32\bin;c:\cygnus\cygwin-b20\H-i586-cygwin32\bin;d:\cfn\bin;
D:\orant\bin;C:\WINNT\system32;
C:\WINNT;C:\Program Files\Dell\OpenManage\ResolutionAssistant\Common\bin;
d:\Program Files\Symantec\pcAnywhere;
C:\Program Files\Executive Software\DiskeeperServer\;}

Java is prepending itself! That confused me--- and broke my exec from ant.

Belorussian translation

Read environment variables (JDK1.5)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0466.html

Read environment variables (JDK1.5) 145


Real's HowTo PDF version

JDK1.5
System.getenv() is back!

import java.util.*;

public class Test {


public static void main(String args[]) {
// just one
System.out.println("PATH = " + System.getenv("PATH"));
// all of them
Map env = System.getenv();
for (Iterator it=env.entrySet().iterator(); it.hasNext(); ) {
Map.Entry entry = (Map.Entry)it.next();
System.out.println(entry.getKey() + " = " + entry.getValue());
}
}
}

See also this HowTo.

See this Howto for common XP environment variables

Read environment variables (JNI)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0460.html

For some odd reasons, the getenv() method was removed from the JDK. Rumors is that a mechanism to
retrieve an environment will be back in JDK1.5 (see this HowTo). But for now, you can use -D switch to
retrieve named environment variable and pass them to the JVM (see this HowTo) or use this JNI routine :

JNIEXPORT jstring JNICALL JavaHowTo_getenv


(JNIEnv *env, jclass c, jstring jname){
if ( jname == NULL ) {
return NULL ;
}
const char *name =
(*env)->GetStringUTFChars(env, jname, (jboolean *)NULL) ;
const char *value = getenv(name) ;
(*env)->ReleaseStringUTFChars(env, jname, name) ;
return value ? (*env)->NewStringUTF(env, value) : NULL ;
}

NOTE : This is fine if the environment variable contains only regular 7-bit ASCII characters.

See also this HowTo.

Read environment variables (JNI) 146


Real's HowTo PDF version

Use a MAKE file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0158.html

# jMAKEFILE a MAKEFILE for JAVA development


# (Microsoft nMAKE)
# nmake /f j.makefile.mak doc
# to generate JAVADOC

.SUFFIXES: .class .java

JAVAHOME=c:\windev\jdk1.1.3
JAVAC= $(JAVAHOME)\bin\javac
PATH=$(JAVAHOME)\bin;$(PATH)
CLASSPATH=.;$(JAVAHOME)\lib\classes.zip;$(JSDKHOME)\lib\classes.zip
DEST=.
DOC=.
JAVA=$(JAVAHOME)\bin\java
JAVACFLAGS=-deprecation

.SUFFIXES: .java .class

.java.class:
$(JAVAC) -classpath $(CLASSPATH) $(JAVACFLAGS) $<

CLASSFILES = GetImage.class \
myCanvas.class

SOURCEFILES = GetImage.java \
myCanvas.java

# begin ---- JAR support ----------


JARFILE= theJAR.jar

$(JARFILE): $(CLASSFILES) $(SOURCEFILES)


jar cfm0 $(JARFILE) <<manifest.tmp $(CLASSFILES)
$(DATAFILES)
Name: GetImage.class
Java-Bean: False

Name: myCanvas.class
Java-Bean: True
<<
# end ---- JAR support ----------

all : $(JARFILE) $(CLASSFILES) doc

doc : $(CLASSFILES)

Use a MAKE file 147


Real's HowTo PDF version

javadoc -version -author -d $(DOC) $(SOURCEFILES)

install :
copy $CLASSESFILE $(DEST)

clean:
del $(CLASSFILES)

Detect the browser/JVM type


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0160.html

This HowTo is obsolete. Check this one instead : Detect browser type from an Applet
One way is to instanciate a known browser-specific method and catch the Exception if not found
import java.applet.*;

public class BrowserDetector extends Applet {


public void init() {
if ( isNetscape() )
System.out.println("This browser is a Netscape Browser.");
if ( isMicrosoft() )
System.out.println("This browser is a Microsoft Browser.");
}

public static boolean isNetscape() {


try {
Class.forName("netscape.applet.MozillaAppletContext");
}
catch (ClassNotFoundException e) {
System.out.println("This browser is not a Netscape Browser.");
return false;
}
return true;
}

public static boolean isMicrosoft() {


try {
Class.forName("com.ms.applet.GenericAppletContext");
}
catch (ClassNotFoundException e) {
System.out.println("This browser is not a Microsoft Browser.");
return false;
}
return true;
}
}

Or by examining the string representation of the getAppletContext() method

Detect the browser/JVM type 148


Real's HowTo PDF version

String theBrowser = "APPLICATION";


String appletContext = getAppletContext().toString();
if (appletContext.startsWith("sun.applet.AppletViewer"))
theBrowser = "APPLETVIEWER";
else if (appletContext.startsWith("netscape.applet."))
theBrowser = "NETSCAPE";
else if (appletContext.startsWith("com.ms.applet."))
theBrowser = "MICROSOFT";
else if (appletContext.startsWith("sunw.hotjava.tags.TagAppletPanel"))
theBrowser = "HOTJAVA";
else if (appletContext.startsWith( "sun.plugin.navig.win32.AppletPlugin"))
theBrowser = "NETSCAPEPLUGIN";
else if (appletContext.startsWith( "sun.plugin.ocx.ActiveXApplet"))
theBrowser = "MICROSOFTPLUGIN;
else if (appletContext.startsWith
( "sun.plugin.viewer.context.IExplorerAppletContext")
theBrowser = "MICROSOFTPLUGINJRE1.4;

For an application, by looking at the string representation of the getDefaultToolkit() method, we detect the
JVM type

String theJVM = "";


String toolkit = Toolkit.getDefaultToolkit().toString();

if (theBrowser.equals("APPLICATION") {
if (toolkit.startsWith( "sun.awt.windows.WToolkit"))
theJVM = "JAVA";
else if (toolkit.startsWith( "com.ms.awt.WToolkit"))
theJVM = "JVIEW";
}

For example, our MyApplet.class exists in three versions. One is using Microsoft-specific classes, the other is
a JDK1.1 applet and finally a version for JDK102-only browser. The idea is to put all the required classes in
an ARCHIVE file. By using a javascript entities, we decide which archive to use. During layout time, the
javascript entity is remplaced by the right archive name.

<HTML></HTML><HEAD>
<SCRIPT>
function isBrowser(b,v) {
browserOk = false;
versionOk = false;
browserOk = (navigator.appName.indexOf(b) != -1);
versionOk = (v <= parseInt(navigator.appVersion));
return browserOk && versionOk;
}

archiveToBeUsed = "java102.jar";

if (isBrowser("Microsoft", 4)) {
archiveToBeUsed = "ie4.jar";
}
else {

Detect the browser/JVM type 149


Real's HowTo PDF version

if isBrowser("Netscape", 4) {
archiveToBeUsed = "n4.jar";
}
}

</SCRIPT></HEAD><BODY>
<APPLET CODE ="MyApplet.class"
HEIGHT=100
WIDTH=400
ARCHIVE=&{archiveToBeUsed}; >
</APPLET>
</BODY></HTML>

NOTE: You may need to use the document.write() method to generate the right APPLET tag instead of a the Javascript entity to be compatible with Netscape
and IE.

Fix the "Wrong magic number" error message


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0163.html

The "magic number" is represented by the first few bytes of a given file. It is used to identified the file type.

For Java classes, the magic number is 0xCAFEBABE (you can verify this by viewing a class file with
hexadecimal editor or the DOS Debug utility). This is used by the browser JVM as a quick check of whether
the called file is really a Java class.

If the message is displayed and you are sure that you have uploaded a "real" class to web server then it's
probably because the FTP download has been done in TEXT mode instead of BINARY so the resulting file on
the server is corrupted.

Use a precompiler "à la C" with Java


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0164.html

Open source packages

Check this list of what is available.

Also take a look at JEnable

Fix the "Wrong magic number" error message 150


Real's HowTo PDF version

Ant

For simple need, Ant can be used to do substitution in your sources.

We insert into the code a special tag to delimit code that need to be stripped by the Ant script. Let's say we use
//@STARTDEBUG@// and //@ENDDEBUG@//.

package com.rgagnon.howto;

import javax.swing.JFrame;

public class Example {

public static void main(String args[]){


JFrame f = new JFrame();
f.setSize(300,200);
f.setVisible(true);
f.setTitle("HowTo");
//@STARTDEBUG@//
f.setTitle(f.getTitle() + " DEBUG version");
//@ENDDEBUG@//
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}

If you execute this code, the JFrame title will have the word "DEBUG" appended to it.

The Ant script to remove the debugging code is :

<project default="buildme">

<target name="compileprod">
<copy todir="../out" includeEmptyDirs="false">
<filterchain>
<tokenfilter>
<replacestring from="//@STARTDEBUG@//" to="/*" />
<replacestring from="//@ENDDEBUG@//" to="*/" />
</tokenfilter>
</filterchain>
<fileset dir=".">
<include name="**/*.java" />
</fileset>
</copy>

<javac srcdir="../out" />


</target>

<target name="compiledebug">
<javac srcdir="." />
</target>

Use a precompiler "à la C" with Java 151


Real's HowTo PDF version

<target name="buildme" depends="compileprod" />


</project>

After running this script, the source (in the ..\out directory)

package com.rgagnon.howto;

import javax.swing.JFrame;

public class Example {

public static void main(String args[]){


JFrame f = new JFrame();
f.setSize(300,200);
f.setVisible(true);
f.setTitle("HowTo");
/*
f.setTitle(f.getTitle() + " DEBUG version");
*/
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}

Simple boolean flag

See this HowTo. This technique relies on the compiler optimization which remove code in the bytecode
generated because it will never be executed.

Determine what are the classes actually used


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0165.html

In Netscape

1. Open the Java console


2. Press "9" to set the Debug level
3. Execute your applet.
4. Check the console and take note of the loaded classes.

In application

java -verbose:class MyApp

NOTE: This can be useful if you want to trim a JAR to include only classes actually used.

Use a precompiler "à la C" with Java 152


Real's HowTo PDF version

Set the memory available to the JVM


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0131.html

If your program allocates a lot of memory, you may need to increase this value to give more room to the
garbage collector.

When starting the JVM, two parameters can be adjusted to suit your memory needs :

-Xms<size> specifies the initial Java heap size and


-Xmx<size> the maximum Java heap size.

To set the minimum at 64Mb and the maximum at 256Mb

java -Xms64m -Xmx256m ...

The default value for the minimum is 2Mb, for the maximum it's 64Mb.

Generate the Javadoc "en français"


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0437.html

The javadoc utility uses the regular Java mechanism to internationalize its output. The tools.jar in the lib
directory contains the resource bundle standard.properties used by Javadoc to generated the labels. To add a
new language, you need to create the appropriate resource bundle, in our case for french, we need a file called
standard_fr.properties.

The new file must be in the package com.sun.tools.doclets.standard.resources.

Extract from tools.jar, the standard.properties files (keep the directory structure). Copy it under the name
standard_fr.properties. Translate it (or you can download my "incomplete" version here).

[standard.properties (extract)]

doclet.Window_Split_Index={0}\: {1}-Index
doclet.Packages=Packages
doclet.SerialData=Serial Data\:
doclet.Since=Since\:
doclet.Warn_inline_taglet=Inline tag {0} should only be used with a {1}.
doclet.ClassUse_Subinterface=Subinterfaces of {0} in {1}
doclet.Frame_Version=Frame version
doclet.Generated_Docs_Untitled=Generated Documentation (Untitled)

Set the memory available to the JVM 153


Real's HowTo PDF version

[standard_fr.properties (extract)]

doclet.Window_Split_Index={0}\: {1}-Index
doclet.Packages=Paquetages
doclet.SerialData=Donn\u00E9e s\u00E9rialis\u00E9e\:
doclet.Since=Depuis\:
doclet.Warn_inline_taglet=Inline tag {0} should only be used with a {1}.
doclet.ClassUse_Subinterface=Sous-interfaces de {0} dans {1}
doclet.Frame_Version=Version avec cadres
doclet.Generated_Docs_Untitled=Documentation g\u00E9n\u00E9r\u00E9e

Once everything translated, put your standard_fr.properties into the tools.jar making sure that the file is
located in the right package (along standard.properties in com.sun.tools.doclets.standard.resources).

To generate in french, use the -locale switch on the command line

javadoc -locale fr ....

NOTE : Make sure the -locale switch is the first one.

Using Ant,

<javadoc
locale="fr"
sourcefiles="c:/client/Client.java"
destdir="javadoc/Client"
author="true"
version="true"
use="true"
private="true"
windowtitle="Client">
<doctitle><![CDATA[<h1>Client</h1>]]></doctitle>
<bottom><![CDATA[<i>Copyright &#169; 2003 Real's Howto.</i>]]></bottom>
</javadoc>

Use JDK1.5 new features


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0462.html

• Download the JDK1.5 and install it.


• From a shell, type
&GT; java -version

The response should be something like

java version "1.5.0-beta"

Generate the Javadoc "en français" 154


Real's HowTo PDF version

Java(TM) 2 Runtime Environment, Standard Edition (build 1.5.0-beta-b32c)


JAVA HOTSPOT(TM) CLIENT VM (BUILD 1.5.0-BETA-B32C, MIXED MODE)

On Windows, if you have a "file not found" message, it's because the JVM can't be found through the
PATH. Do it again but with the complete path (if the path contains spaces, make sure to use quotes!) :

&GT; "c:\program files\java\j2sdk1.5.0\bin\java" -version


• Let's do our first jdk1.5 program :
public class Test15 {
public static void main(String ... args) {
System.out.printf("Local time: %tT", java.util.Calendar.getInstance());
}
}
• Compile it (again you may need to specify the complete path to the compiler if the PATH is not set
correctly):
&GT; "c:\program files\java\j2sdk1.5.0\bin\javac" -source 1.5 Test15.java

Note the switch "-source 1.5", if you don't specify it you won't be able to access the new features (like
System.out.printf()).
• Run it
>"C:\Program Files\Java\j2sdk1.5.0\bin\java" Test15
Local time: 15:26:04

Check the class version


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0544.html

The first 4 bytes are a magic number, 0xCAFEBABe, to identify a valid class file then the next 2 bytes
identify the class format version (major and minor).

Possible major/minor value :

major minor Java platform version


45 3 1.0
45 3 1.1
46 0 1.2
47 0 1.3
48 0 1.4
49 0 1.5
50 0 1.6
51 0 1.7
52 0 1.8

import java.io.*;

public class ClassVersionChecker {


public static void main(String[] args) throws IOException {

Use JDK1.5 new features 155


Real's HowTo PDF version

for (int i = 0; i < args.length; i++)


checkClassVersion(args[i]);
}

private static void checkClassVersion(String filename)


throws IOException
{
DataInputStream in = new DataInputStream
(new FileInputStream(filename));

int magic = in.readInt();


if(magic != 0xcafebabe) {
System.out.println(filename + " is not a valid class!");;
}
int minor = in.readUnsignedShort();
int major = in.readUnsignedShort();
System.out.println(filename + ": " + major + " . " + minor);
in.close();
}
}

> java ClassVersionChecker ClassVersionChecker.class


ClassVersionChecker.class: 49 . 0

from The Java Virtual Machine Specification

magic
The magic item supplies the magic number identifying the class file format; it has the value 0xCAFEBABE.

minor_version, major_version
The values of the minor_version and major_version items are the minor and major version numbers of this
class file.Together, a major and a minor version number determine the version of the class file format. If a
class file has major version number M and minor version number m, we denote the version of its class file
format as M.m. Thus, class file format versions may be ordered lexicographically, for example, 1.5 < 2.0 <
2.1.

A Java virtual machine implementation can support a class file format of version v if and only if v lies in
some contiguous range Mi.0 v Mj.m. Only Sun can specify what range of versions a Java virtual machine
implementation conforming to a certain release level of the Java platform may support.

Get the system properties or the JVM uptime


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0549.html

The RuntimeMXBean defines several convenient methods for accessing system properties about the Java
virtual machine.

Check the class version 156


Real's HowTo PDF version

[J2SE 1.5]

import java.util.Date;

import java.lang.management.RuntimeMXBean;
import java.lang.management.ManagementFactory;

class JMXTest {
public static void main(String args[]) {
JMXTest x = new JMXTest();
x.doit();
}

public void doit() {


try{
RuntimeMXBean mx = ManagementFactory.getRuntimeMXBean();
System.out.println("BOOTCLASSPATH:\n" + mx.getBootClassPath());
System.out.println("CLASSPATH:\n" + mx.getClassPath());

// the input arguments passed to the Java virtual machine


// which does not include the arguments to the main method.
System.out.println("COMMAND LINE ARGS:\n" + mx.getInputArguments());
// a map of names and values of all system properties.
System.out.println("SYSTEM PROPERTIES:\n" + mx.getSystemProperties());

System.out.println("VM start time : " + new Date(mx.getStartTime()));


System.out.println("VM up time : " + mx.getUptime() + " ms");

}
catch (Exception e) {
e.printStackTrace();
}
}
}

Detect if running in a 64bit JVM


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0565.html

public static boolean is64BitVM() {


String bits = System.getProperty("sun.arch.data.model", "?");
if (bits.equals("64") {
return true;
}
if (bits.equals("?") {
// probably sun.arch.data.model isn't available
// maybe not a Sun JVM?
// try with the vm.name property
return

Get the system properties or the JVM uptime 157


Real's HowTo PDF version

System.getProperty("java.vm.name")
.toLowerCase().indexOf("64") >= 0;
}
// probably 32bit
return false;
}
}

Set the default JVM type


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0566.html

If you type, in a Shell

> java -version

you get

java version "1.5.0"


Java(TM) 2 Runtime Environment, Standard Edition (build 1.5.0-b64)
Java HotSpot(TM) Client VM (build 1.5.0-b64, mixed mode, sharing)

The default JVM with a JIT (Just-In-Time compiler) for a "client" mode is used. The other available mode is
"server".

From the Hot Spot FAQ at http://java.sun.com/docs/hotspot/HotSpotFAQ.html#compiler_types.

What's the difference between the -client and -server systems?

These two systems are different binaries. They are essentially two different compilers (JITs)interfacing to the
same runtime system. The client system is optimal for applications which need fast startup times or small
footprints, the server system is optimal for applications where the overall performance is most important. In
general the client system is better suited for interactive applications such as GUIs. Some of the other
differences include the compilation policy,heap defaults, and inlining policy.

Where do I get the server and client systems?

Client and server systems are both downloaded with the 32-bit Solaris and Linux downloads. For 32-bit
Windows, if you download the JRE, you get only the client, you'll need to download the SDK to get both
systems.

For 64-bit, only the server system is included. On Solaris, the 64-bit JRE is an overlay on top of the 32-bit
distribution. However, on Linux and Windows, it's a completely separate distribution. The default setting is
defined the file jvm.cfg.

Detect if running in a 64bit JVM 158


Real's HowTo PDF version

On Debian GNU/Linux with Sun Java 1.5.0, the file is in /etc/java-1.5.0-sun.


On Windows, it's in C:\Program Files\Java\jre1.5.0\lib\i386.

A content like

-client KNOWN
-server KNOWN

defines the client as the default.

-server KNOWN
-client KNOWN

sets the server as the default.

Select a particular JRE from the command line


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0634.html

It's possible to have many JRE side-by-side on a computer.

If the JRE is properly installed on Windows, informations about each version are stored in the registry. The
installation process installs a special java.exe in the system PATH. So you don't need to alter you PATH
because this special java.exe will find the current JRE. From a command line, type java -version to display the
current jre version installed.

With release 1.6, it's now possible to select a different JRE installation than the last one without any registry
modification.

The JRE installation are listed in the registry in the key


HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment

Take this simple test class

public class ShowVersion {


public static void main(String args[]) {
System.out.println(System.getProperty("java.version"));
}
}

On a system, with 1.6 and 1.5 installed. If you type

> java ShowVersion

Set the default JVM type 159


Real's HowTo PDF version

It's probably the 1.6 JRE that will be used since it's the last installed.

To force the 1.5 JRE instead, use this command line.

> java -version:"1.5" ShowVersion

If the bytecode is incompatible with the given JRE then .. it won't work, of course.

ref : Java 6 technotes

You can always give the complete path to use a specific installation. Launching the JVM this way does not
use the registry setting at all.

>"C:\Program Files\Java\j2re1.4.1_02\bin\java" -version


java version "1.4.1_02"

Get the PID (pure Java solution)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0651.html

This solution use the RuntimeMXBean. The name of the bean contains the pid (ex. 12345@localhost).

Warning : The returned name string can be any arbitrary string and a Java virtual machine implementation can
choose to embed platform-specific useful information in the returned name string.

On the Sun JVM (Windows plateform), the PID is present.

public class SystemUtils {

private SystemUtils() {}

public static long getPID() {


String processName =
java.lang.management.ManagementFactory.getRuntimeMXBean().getName();
return Long.parseLong(processName.split("@")[0]);
}

public static void main(String[] args) {


String msg = "My PID is " + SystemUtils.getPID();

javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, msg, "SystemUtils", javax.swing.JOptionPane.DEFAULT_OPTION);

Select a particular JRE from the command line 160


Real's HowTo PDF version

The result is

For a Java-JNI solution, see this HowTo.

Get the PID (JNI solution)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0467.html

class JavaHowTo {
public native long getCurrentProcessId();
static {
System.loadLibrary("jni2");
}
}

public class JNIJavaHowTo {


public static void main(String[] args) {
JavaHowTo jht = new JavaHowTo();
System.out.println("Press Any key...");
java.io.BufferedReader input =
new java.io.BufferedReader(new java.io.InputStreamReader(System.in));
try { input.readLine();}
catch (Exception e) { e.printStackTrace();}
System.out.println(jht.getCurrentProcessId());
}
}

// jni2.cpp : Defines the entry point for the DLL application.


//

#include "stdafx.h"
#include <process.h>
#include "JavaHowTo.h"

Get the PID (pure Java solution) 161


Real's HowTo PDF version

BOOL APIENTRY DllMain( HANDLE hModule,


DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
return TRUE;
}

JNIEXPORT jlong JNICALL Java_JavaHowTo_getCurrentProcessId


(JNIEnv *, jobject) {

// return GetCurrentProcessId();
return getpid();
}

You can download the whole thing here.

For a Java-only solution, see this HowTo

Set default value for Java property or JVM option (system wide)
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-set-java-properties-system-wide.html

If you find yourself using the same options over and over before laucing a java process, you can set up a
special environment variable to contain your default options and the JVM will pick up the the values.

If the Java process is launch via java.exe then the environment variable is called _JAVA_OPTIONS,

e.g. In Windows:

set _JAVA_OPTIONS=-Xms64m -Xmx128m -Dawt.useSystemAAFontSettings=lcd

In Linux:

export _JAVA_OPTIONS='-Xms64m -Xmx128m -Dawt.useSystemAAFontSettings=lcd'

ref : http://java.sun.com/j2se/1.5.0/docs/guide/2d/flags.html

If the Java process is launch via javaw.exe (Applet) then the environment variable is called
_JPI_VM_OPTIONS.

For example :

_JPI_VM_OPTIONS = -Dsome.property=true

Get the PID (JNI solution) 162


Real's HowTo PDF version

For a Java Web Start process (javaws.exe), the environment variable is called JAVAWS_VM_ARGS.

For example :

JAVAWS_VM_ARGS = -Dsome.property=true

ref : http://docs.oracle.com/javase/7/docs/webnotes/tsg/TSG-Desktop/html/plugin.html#gcexdd

Detect if running in debug mode


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-detect-if-running-in-debug-mode.html

If you want to detect if your program is running in debug mode (ex. Eclipse).

public class Test {


public static void main(String args[]) {
boolean isDebug =
java.lang.management.ManagementFactory.getRuntimeMXBean().
getInputArguments().toString().indexOf("-agentlib:jdwp") > 0;
System.out.println("In debug : " + isDebug);
}
}

Configure Java deployment with properties


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-configure-java-deployment-with-properties.html

User level

The deployment.properties file is used for storing and retrieving deployment configuration properties
shown in the Java Control Panel. The properties are also used for customizing runtime behavior for both Java
Plug-in and Java Web Start.

Location of the deployment.properties :

• Windows - <User Application Data


Folder>\LocalLow\Sun\Java\Deployment\deployment.properties
• Linux - ${user.home}/.java/deployment/deployment.properties
• OS X - ~/Library/Application
Support/Oracle/Java/Deployment/deployment.properties

Set default value for Java property or JVM option (system wide) 163
Real's HowTo PDF version

On the Windows, <User Application Data Folder> is typically C:\Users\<your username>\AppData (or
%APPDATA%) which is hidden by default.

ref : Oracle Java documentation

List of possible deployment properties

#deployment.properties https://gist.githubusercontent.com/MyITGuy/9628895/raw/3727348918e036ba

# Security Tab
# Enable Java content in the browser
deployment.webjava.enabled=true
deployment.webjava.enabled.locked
# Security Level
deployment.security.level=MEDIUM
deployment.security.level.locked

# Advanced Tab
# Debugging\Enable tracing
deployment.trace=false
deployment.trace.locked
# Debugging\Enable logging
deployment.log=false
deployment.log.locked
# Debugging\Show applet lifecycle exceptions
deployment.javapi.lifecycle.exception=false
deployment.javapi.lifecycle.exception.locked
# Java console
deployment.console.startup.mode.locked
deployment.console.startup.mode=HIDE
# Default Java for browsers\Microsoft Internet Explorer
deployment.browser.vm.iexplorer=true
deployment.browser.vm.iexplorer.locked
# Default Java for browsers\Mozilla family
deployment.browser.vm.mozilla.locked
deployment.browser.vm.mozilla=false
# Java Plug-in\Enable the next-generation Java Plug-in (requires browser restart)
# This must be done by executing one of the following commands as an administrator:
# [Disable] - {JREInstallPath}\bin\ssvagent.exe -high -jpisetup -old
# [Enable] - {JREInstallPath}\bin\ssvagent.exe -high -jpisetup -new
# Shortcut Creation
deployment.javaws.shortcut=ASK_IF_HINTED
deployment.javaws.shortcut.locked
# JNLP File/MIME Association
deployment.javaws.associations=ASK_USER
deployment.javaws.associations.locked
# Application Installation
deployment.javaws.install=IF_HINT
deployment.javaws.install.locked
#JRE Auto-Download
deployment.javaws.autodownload=NEVER
deployment.javaws.autodownload.locked
# Security Execution Environment\Enable granting elevated access to signed apps

Configure Java deployment with properties 164


Real's HowTo PDF version

# aka. Allow user to grant permissions to signed content


deployment.security.askgrantdialog.show=true
deployment.security.askgrantdialog.show.locked
# Security Execution Environment\Enable granting elevated access to self-signed apps
deployment.security.askgrantdialog.notinca=true
deployment.security.askgrantdialog.notinca.locked
# Security Execution Environment\Show sandbox warning banner
deployment.security.sandbox.awtwarningwindow=true
deployment.security.sandbox.awtwarningwindow.locked
# Security Execution Environment\Allow user to accept JNLP security requests
deployment.security.sandbox.jnlp.enhanced=true
deployment.security.sandbox.jnlp.enhanced.locked
# Security Execution Environment\Don't prompt for client certificate selection when no certific
deployment.security.clientauth.keystore.auto=true
deployment.security.clientauth.keystore.auto.locked
# Security Execution Environment\Warn if site certificate does not match hostname
deployment.security.jsse.hostmismatch.warning=true
deployment.security.jsse.hostmismatch.warning.locked
# Security Execution Environment\Show site certificate from server even if it is valid
deployment.security.https.warning.show=false
deployment.security.https.warning.show.locked
# Mixed code (sandbox vs. trusted) security verification
deployment.security.mixcode=DISABLE
deployment.security.mixcode.locked
# Perform certificate revocation checks on
deployment.security.revocation.check=ALL_CERTIFICATES
deployment.security.revocation.check.locked
# Check for certificate revocation using
# Replaces Advanced Security Settings\Check certificates for revocation using Certificate Revoc
# [Certificate Revocation List (CRLs)] - ocsp=false, crl=true
# [Online Certificate Status Protocol (OCSP)] - ocsp=true, crl=false
# [Bot CRLs and OCSP] - ocsp=true, crl=true
deployment.security.validation.ocsp=true
deployment.security.validation.ocsp.locked
deployment.security.validation.crl=true
deployment.security.validation.crl.locked
# Advanced Security Settings\Use certificates and keys in browser keystore
deployment.security.browser.keystore.use=true
deployment.security.browser.keystore.use.locked
# Advanced Security Settings\Check certificates for revocation using Certificate Revocation Lis
# See Check for certificate revocation using
# Advanced Security Settings\Enable list of trusted publishers
deployment.security.pretrust.list=true
deployment.security.pretrust.list.locked
# Advanced Security Settings\Enable blacklist revocation check
deployment.security.blacklist.check=true
deployment.security.blacklist.check.locked
# Advanced Security Settings\Enable caching password for authentication
deployment.security.password.cache=true
deployment.security.password.cache.locked
# Advanced Security Settings\Enable online certifcate validation
deployment.security.revocation.check=NO_CHECK
deployment.security.revocation.check.locked
# Advanced Security Settings\Use SSL 2.0 compatible ClientHello format

Configure Java deployment with properties 165


Real's HowTo PDF version

deployment.security.SSLv2Hello=false
deployment.security.SSLv2Hello.locked
# Advanced Security Settings\Use SSL 3.0
deployment.security.SSLv3=true
deployment.security.SSLv3.locked
# Advanced Security Settings\Use TLS 1.0
deployment.security.TLSv1=true
deployment.security.TLSv1.locked
# Advanced Security Settings\Use TLS 1.1
deployment.security.TLSv1.1=false
deployment.security.TLSv1.1.locked
# Advanced Security Settings\Use TLS 1.2
deployment.security.TLSv1.2=false
deployment.security.TLSv1.2.locked
# Miscellaneous\Place Java icon in system tray
# Miscellaneous\Java Quick Starter
deployment.system.tray.icon=false
deployment.system.tray.icon.locked

# Screen: Your Java version is insecure. or Your Java version is out of date.
deployment.expiration.check.enabled=false
deployment.expiration.check.enabled.locked
#
deployment.capture.mime.types=true
deployment.capture.mime.types.locked

deployment.security.expired.warning=false
deployment.security.expired.warning.locked

deployment.user.security.exception.sites=C:\\WINDOWS\\Sun\\Java\\Deployment\\exception.sites
deployment.user.security.exception.sites.locked
# Java 7 Update 10
deployment.expiration.decision.10.10.2.locked
deployment.expiration.decision.10.10.2=later
deployment.expiration.decision.suppression.10.10.2.locked
deployment.expiration.decision.suppression.10.10.2=true
deployment.expiration.decision.timestamp.10.10.2.locked
deployment.expiration.decision.timestamp.10.10.2=2/28/2014 12\:1\:31

Example of a deployment.properties

#deployment.properties
deployment.webjava.enabled=true
deployment.security.level=MEDIUM
deployment.security.level.locked
deployment.user.security.exception.sites=c\:/Windows/Sun/Java/Deployment/exception.sites

The exception.sites file is a one URL per line list of sites that you want in the Exception Site List field
found in the Java Control Panel. Nothing else goes in this file.

Configure Java deployment with properties 166


Real's HowTo PDF version

System level

The deployment.config file is used for specifying the system-level deployment.properties in the
infrastructure. By default no deployment.config file exists, so no system-wide deployment.properties file
exists.

Possible location of the deployment.config :

• Windows - <Windows Directory>\Sun\Java\Deployment\deployment.config or


${deployment.java.home}\lib\deployment.config
• Linux - /etc/.java/deployment/deployment.config or
${deployment.java.home}/lib/deployment.config
• OS X - /Library/Application
Support/Oracle/Java/Deployment/deployment.config or
${deployment.java.home}/lib/deploy/deployment.config

The deployment.config file contains two properties: deployment.system.config and


deployment.system.config.mandatory.

The deployment.system.config property is the URL to the system (enterprise-wide) deployment.properties


file. This property can be used by system administrators to centrally administer or "lock-down" user-specific
configuration settings. For local files, use the file protocol in the URL, for example,
file:///C:/Windows/Sun/Java/Deployment/deployment.properties.

The deployment.system.config.mandatory property is a boolean. If set to true, the deployment.properties file


that is pointed to by the deployment.system.config property must be found and successfully loaded, otherwise,
nothing is allowed to run. If the property is set to false, an attempt is made to find and load the deployment.
properties file that is pointed to by the deployment.system.config property. If successful, the file is used,
otherwise, the file is ignored. The default for the deployment.system.config.mandatory property is false.

deployment.system.config=file\://ourserver.local/deploy/Sun/Java/Deployment/deployment.properti
deployment.system.config.mandatory=true

This example points to a deployment.properties file on a DFS path //ourserver.local/deploy/. Since the
property deployment.system.config.mandatory=true then if the deployment.properties file is not found, then
nothing is allowed to run.

Wrap a Java bean in a COM object (using Sun ActiveX bridge)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0045.html

The previous How-to was using a Microsoft utility to enable access to Java objects from a COM-aware
development tool. Sun provides a similar tool but you must package everything in a jar file and use the Beans

Configure Java deployment with properties 167


Real's HowTo PDF version

technology. The tool is called packager, written in Java, you execute it from the sun.beans.ole package. The
Java Plug-in 1.2 and the JDK1.2 must be installed on the system (for download, see Java Sun Web site).

Let's try it with this simple class :

package JavaCom;
public class JavaBeanSays {
private String _hello = "Hello World!";

public String getHello() {


return _hello ;
}

public void setHello(String s) {


_hello = s;
}
}

NOTE: This is not really a Bean but let's keep it simple!

The next step is to build a manifest file to identify the bean in the jar. Here it is (manifest.txt):

Name: JavaCom/JavaBeanSays
Java-Bean: true

NOTE: If no manifest is present all classes in the jar are treated as beans.

The JavaBeanSays class is in the directory JavaCom, the manifest.txt is the directory under it. From the
directory under (the one containing manifest.txt), we built the jar with :

jar cfm javacom.jar manifest.txt javacom\JavaBeanSays.class

NOTE: You can download my JavaCom.jar if you to proceed more rapidly.

The next step is to run the packager. You run it from the JDK installation directory. If the JDK is installed in
c:\dev\java\jdk1.2.1\ for example , you go there. And you start the packager with

bin\java.exe -cp jre\lib\rt.jar;jre\lib\jaws.jar sun.beans.ole.Packager

A wizard is started, you follow the 5 steps to create the "JavaBeans bridge for ActiveX" for the JavabeanSays
component.

The first step is to specify where is located the JavaCom.jar file. When selected, the wizard should list the
JavaCom.JavaBeanSays bean, press Next. The "ActiveX" name under which the beans will be seen is shown,
press Next (in VbScript, the beans suffix must be added to this name).

An output directory is needed, be careful because this directory name will be hard-coded in the generated files
(REG and TLB), you need to specify a valid directory name. The packager assume that a subdirectory bin is
present with the file beans.ocx in it. You can create it and then copy beans.ocx from the JRE\bin into it or edit

Wrap a Java bean in a COM object (using Sun ActiveX bridge) 168
Real's HowTo PDF version

the REG file to specify the original JRE\bin and update the registry with the good location.

The Bean is now registered and ready to be used as a COM object.

NOTE: There is a command-line interface available in the packager if you want to bypass the wizard.

To test it, try this VbScript (TestJavaBeansSays.vbs)

' VBSCRIPT connect to a Java Bean


Dim objJava
Set objJava = WScript.CreateObject("JavaBeanSays.Bean")

strFromJava = objJava.getHello
MsgBox strFromJava, _
0, _
"JAVA BEAN OUTPUT"

objJava.setHello("Bonjour le monde!")

strFromJava = objJava.getHello
MsgBox strFromJava, _
0, _
"JAVA BEAN OUTPUT"

NOTE: Check the JAVA PLUG-IN SCRIPTING documentation (jdk1.2) or (jsdk1.4). document for more infos.

Query the Windows Registry (reg.exe)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0480.html

We launch the REG utility and capture the output. The performance is poor so it's a good idea to cache
frequently used values.

Note : The Microsoft Windows NT Server 4.0 Resource Kit contains REG.EXE. In Windows 2000 and later REG.EXE is a native command. The REG utility
can be used to write values in the registry (reg add /? for more infos).

In this example,we query the registry to extract the personal folder path ("My Documents") and the processor
ID and its name.

import java.io.*;

public class RegQuery {

private static final String REGQUERY_UTIL = "reg query ";


private static final String REGSTR_TOKEN = "REG_SZ";
private static final String REGDWORD_TOKEN = "REG_DWORD";

private static final String PERSONAL_FOLDER_CMD = REGQUERY_UTIL +

Query the Windows Registry (reg.exe) 169


Real's HowTo PDF version

"\"HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\"
+ "Explorer\\Shell Folders\" /v Personal";
private static final String CPU_SPEED_CMD = REGQUERY_UTIL +
"\"HKLM\\HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0\""
+ " /v ~MHz";
private static final String CPU_NAME_CMD = REGQUERY_UTIL +
"\"HKLM\\HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0\""
+ " /v ProcessorNameString";

public static String getCurrentUserPersonalFolderPath() {


try {
Process process = Runtime.getRuntime().exec(PERSONAL_FOLDER_CMD);
StreamReader reader = new StreamReader(process.getInputStream());

reader.start();
process.waitFor();
reader.join();

String result = reader.getResult();


int p = result.indexOf(REGSTR_TOKEN);

if (p == -1)
return null;

return result.substring(p + REGSTR_TOKEN.length()).trim();


}
catch (Exception e) {
return null;
}
}

public static String getCPUSpeed() {


try {
Process process = Runtime.getRuntime().exec(CPU_SPEED_CMD);
StreamReader reader = new StreamReader(process.getInputStream());

reader.start();
process.waitFor();
reader.join();

String result = reader.getResult();


int p = result.indexOf(REGDWORD_TOKEN);

if (p == -1)
return null;

// CPU speed in Mhz (minus 1) in HEX notation, convert it to DEC


String temp = result.substring(p + REGDWORD_TOKEN.length()).trim();
return Integer.toString
((Integer.parseInt(temp.substring("0x".length()), 16) + 1));
}
catch (Exception e) {
return null;
}

Query the Windows Registry (reg.exe) 170


Real's HowTo PDF version

public static String getCPUName() {


try {
Process process = Runtime.getRuntime().exec(CPU_NAME_CMD);
StreamReader reader = new StreamReader(process.getInputStream());

reader.start();
process.waitFor();
reader.join();

String result = reader.getResult();


int p = result.indexOf(REGSTR_TOKEN);

if (p == -1)
return null;

return result.substring(p + REGSTR_TOKEN.length()).trim();


}
catch (Exception e) {
return null;
}
}

static class StreamReader extends Thread {


private InputStream is;
private StringWriter sw;

StreamReader(InputStream is) {
this.is = is;
sw = new StringWriter();
}

public void run() {


try {
int c;
while ((c = is.read()) != -1)
sw.write(c);
}
catch (IOException e) { ; }
}

String getResult() {
return sw.toString();
}
}

public static void main(String s[]) {


System.out.println("Personal directory : "
+ getCurrentUserPersonalFolderPath());
System.out.println("CPU Name : " + getCPUName());
System.out.println("CPU Speed : " + getCPUSpeed() + " Mhz");
}
}

Query the Windows Registry (reg.exe) 171


Real's HowTo PDF version

See also this HowTo and this one.

For a better way to access the Registry, see Read/Write Windows Registry using JNA.

Query/Update the Windows Registry (hack)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0630.html

The JDK contains the required code (java.util.prefs.WindowsPreferences) to access the Windows registry but
to preserve the "purity" of Java, the code is declared as private so it's not visible. The trick is to use reflection
to access private methods defined in the WindowsPreference class.

This technique was first seen in this post.

Remember : This code is a hack and may break anytime. A better alternative is to use JNA.

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;
import java.util.ArrayList;
import java.util.List;
import java.util.prefs.Preferences;

public class WinRegistry {


// inspired by
// http://javabyexample.wisdomplug.com/java-concepts/34-core-java/62-java-registry-wrapper.ht
// http://www.snipcode.org/java/1-java/23-java-class-for-accessing-reading-and-writing-from-w
// http://snipplr.com/view/6620/accessing-windows-registry-in-java/
public static final int HKEY_CURRENT_USER = 0x80000001;
public static final int HKEY_LOCAL_MACHINE = 0x80000002;
public static final int REG_SUCCESS = 0;
public static final int REG_NOTFOUND = 2;
public static final int REG_ACCESSDENIED = 5;

private static final int KEY_ALL_ACCESS = 0xf003f;


private static final int KEY_READ = 0x20019;
private static Preferences userRoot = Preferences.userRoot();
private static Preferences systemRoot = Preferences.systemRoot();
private static Class<? extends Preferences> userClass = userRoot.getClass();
private static Method regOpenKey = null;
private static Method regCloseKey = null;
private static Method regQueryValueEx = null;
private static Method regEnumValue = null;
private static Method regQueryInfoKey = null;
private static Method regEnumKeyEx = null;
private static Method regCreateKeyEx = null;
private static Method regSetValueEx = null;

Query/Update the Windows Registry (hack) 172


Real's HowTo PDF version

private static Method regDeleteKey = null;


private static Method regDeleteValue = null;

static {
try {
regOpenKey = userClass.getDeclaredMethod("WindowsRegOpenKey",
new Class[] { int.class, byte[].class, int.class });
regOpenKey.setAccessible(true);
regCloseKey = userClass.getDeclaredMethod("WindowsRegCloseKey",
new Class[] { int.class });
regCloseKey.setAccessible(true);
regQueryValueEx = userClass.getDeclaredMethod("WindowsRegQueryValueEx",
new Class[] { int.class, byte[].class });
regQueryValueEx.setAccessible(true);
regEnumValue = userClass.getDeclaredMethod("WindowsRegEnumValue",
new Class[] { int.class, int.class, int.class });
regEnumValue.setAccessible(true);
regQueryInfoKey = userClass.getDeclaredMethod("WindowsRegQueryInfoKey1",
new Class[] { int.class });
regQueryInfoKey.setAccessible(true);
regEnumKeyEx = userClass.getDeclaredMethod(
"WindowsRegEnumKeyEx", new Class[] { int.class, int.class,
int.class });
regEnumKeyEx.setAccessible(true);
regCreateKeyEx = userClass.getDeclaredMethod(
"WindowsRegCreateKeyEx", new Class[] { int.class,
byte[].class });
regCreateKeyEx.setAccessible(true);
regSetValueEx = userClass.getDeclaredMethod(
"WindowsRegSetValueEx", new Class[] { int.class,
byte[].class, byte[].class });
regSetValueEx.setAccessible(true);
regDeleteValue = userClass.getDeclaredMethod(
"WindowsRegDeleteValue", new Class[] { int.class,
byte[].class });
regDeleteValue.setAccessible(true);
regDeleteKey = userClass.getDeclaredMethod(
"WindowsRegDeleteKey", new Class[] { int.class,
byte[].class });
regDeleteKey.setAccessible(true);
}
catch (Exception e) {
e.printStackTrace();
}
}

private WinRegistry() { }

/**
* Read a value from key and value name
* @param hkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE
* @param key
* @param valueName
* @return the value

Query/Update the Windows Registry (hack) 173


Real's HowTo PDF version

* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static String readString(int hkey, String key, String valueName)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
if (hkey == HKEY_LOCAL_MACHINE) {
return readString(systemRoot, hkey, key, valueName);
}
else if (hkey == HKEY_CURRENT_USER) {
return readString(userRoot, hkey, key, valueName);
}
else {
throw new IllegalArgumentException("hkey=" + hkey);
}
}

/**
* Read value(s) and value name(s) form given key
* @param hkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE
* @param key
* @return the value name(s) plus the value(s)
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static Map<String, String> readStringValues(int hkey, String key)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
if (hkey == HKEY_LOCAL_MACHINE) {
return readStringValues(systemRoot, hkey, key);
}
else if (hkey == HKEY_CURRENT_USER) {
return readStringValues(userRoot, hkey, key);
}
else {
throw new IllegalArgumentException("hkey=" + hkey);
}
}

/**
* Read the value name(s) from a given key
* @param hkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE
* @param key
* @return the value name(s)
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static List<String> readStringSubKeys(int hkey, String key)
throws IllegalArgumentException, IllegalAccessException,

Query/Update the Windows Registry (hack) 174


Real's HowTo PDF version

InvocationTargetException
{
if (hkey == HKEY_LOCAL_MACHINE) {
return readStringSubKeys(systemRoot, hkey, key);
}
else if (hkey == HKEY_CURRENT_USER) {
return readStringSubKeys(userRoot, hkey, key);
}
else {
throw new IllegalArgumentException("hkey=" + hkey);
}
}

/**
* Create a key
* @param hkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE
* @param key
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static void createKey(int hkey, String key)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int [] ret;
if (hkey == HKEY_LOCAL_MACHINE) {
ret = createKey(systemRoot, hkey, key);
regCloseKey.invoke(systemRoot, new Object[] { new Integer(ret[0]) });
}
else if (hkey == HKEY_CURRENT_USER) {
ret = createKey(userRoot, hkey, key);
regCloseKey.invoke(userRoot, new Object[] { new Integer(ret[0]) });
}
else {
throw new IllegalArgumentException("hkey=" + hkey);
}
if (ret[1] != REG_SUCCESS) {
throw new IllegalArgumentException("rc=" + ret[1] + " key=" + key);
}
}

/**
* Write a value in a given key/value name
* @param hkey
* @param key
* @param valueName
* @param value
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static void writeStringValue
(int hkey, String key, String valueName, String value)

Query/Update the Windows Registry (hack) 175


Real's HowTo PDF version

throws IllegalArgumentException, IllegalAccessException,


InvocationTargetException
{
if (hkey == HKEY_LOCAL_MACHINE) {
writeStringValue(systemRoot, hkey, key, valueName, value);
}
else if (hkey == HKEY_CURRENT_USER) {
writeStringValue(userRoot, hkey, key, valueName, value);
}
else {
throw new IllegalArgumentException("hkey=" + hkey);
}
}

/**
* Delete a given key
* @param hkey
* @param key
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static void deleteKey(int hkey, String key)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int rc = -1;
if (hkey == HKEY_LOCAL_MACHINE) {
rc = deleteKey(systemRoot, hkey, key);
}
else if (hkey == HKEY_CURRENT_USER) {
rc = deleteKey(userRoot, hkey, key);
}
if (rc != REG_SUCCESS) {
throw new IllegalArgumentException("rc=" + rc + " key=" + key);
}
}

/**
* delete a value from a given key/value name
* @param hkey
* @param key
* @param value
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws InvocationTargetException
*/
public static void deleteValue(int hkey, String key, String value)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int rc = -1;
if (hkey == HKEY_LOCAL_MACHINE) {
rc = deleteValue(systemRoot, hkey, key, value);

Query/Update the Windows Registry (hack) 176


Real's HowTo PDF version

}
else if (hkey == HKEY_CURRENT_USER) {
rc = deleteValue(userRoot, hkey, key, value);
}
if (rc != REG_SUCCESS) {
throw new IllegalArgumentException("rc=" + rc + " key=" + key + " value=" + value);
}
}

// =====================

private static int deleteValue


(Preferences root, int hkey, String key, String value)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {
new Integer(hkey), toCstr(key), new Integer(KEY_ALL_ACCESS) });
if (handles[1] != REG_SUCCESS) {
return handles[1]; // can be REG_NOTFOUND, REG_ACCESSDENIED
}
int rc =((Integer) regDeleteValue.invoke(root,
new Object[] {
new Integer(handles[0]), toCstr(value)
})).intValue();
regCloseKey.invoke(root, new Object[] { new Integer(handles[0]) });
return rc;
}

private static int deleteKey(Preferences root, int hkey, String key)


throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int rc =((Integer) regDeleteKey.invoke(root,
new Object[] { new Integer(hkey), toCstr(key) })).intValue();
return rc; // can REG_NOTFOUND, REG_ACCESSDENIED, REG_SUCCESS
}

private static String readString(Preferences root, int hkey, String key, String value)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {
new Integer(hkey), toCstr(key), new Integer(KEY_READ) });
if (handles[1] != REG_SUCCESS) {
return null;
}
byte[] valb = (byte[]) regQueryValueEx.invoke(root, new Object[] {
new Integer(handles[0]), toCstr(value) });
regCloseKey.invoke(root, new Object[] { new Integer(handles[0]) });
return (valb != null ? new String(valb).trim() : null);
}

private static Map<String,String> readStringValues

Query/Update the Windows Registry (hack) 177


Real's HowTo PDF version

(Preferences root, int hkey, String key)


throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
HashMap<String, String> results = new HashMap<String,String>();
int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {
new Integer(hkey), toCstr(key), new Integer(KEY_READ) });
if (handles[1] != REG_SUCCESS) {
return null;
}
int[] info = (int[]) regQueryInfoKey.invoke(root,
new Object[] { new Integer(handles[0]) });

// int count = info[2]; // count


int count = info[0]; // bug fix 20130112
int maxlen = info[3]; // value length max
for(int index=0; index<count; index++) {
byte[] name = (byte[]) regEnumValue.invoke(root, new Object[] {
new Integer
(handles[0]), new Integer(index), new Integer(maxlen + 1)});
String value = readString(hkey, key, new String(name));
results.put(new String(name).trim(), value);
}
regCloseKey.invoke(root, new Object[] { new Integer(handles[0]) });
return results;
}

private static List<String> readStringSubKeys


(Preferences root, int hkey, String key)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
List<String> results = new ArrayList<String>();
int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {
new Integer(hkey), toCstr(key), new Integer(KEY_READ)
});
if (handles[1] != REG_SUCCESS) {
return null;
}
int[] info = (int[]) regQueryInfoKey.invoke(root,
new Object[] { new Integer(handles[0]) });

// int count = info[2]; // count


int count = info[0]; // bug fix 20130112
int maxlen = info[3]; // value length max
for(int index=0; index<count; index++) {
byte[] name = (byte[]) regEnumKeyEx.invoke(root, new Object[] {
new Integer
(handles[0]), new Integer(index), new Integer(maxlen + 1)
});
results.add(new String(name).trim());
}
regCloseKey.invoke(root, new Object[] { new Integer(handles[0]) });
return results;

Query/Update the Windows Registry (hack) 178


Real's HowTo PDF version

private static int [] createKey(Preferences root, int hkey, String key)


throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
return (int[]) regCreateKeyEx.invoke(root,
new Object[] { new Integer(hkey), toCstr(key) });
}

private static void writeStringValue


(Preferences root, int hkey, String key, String valueName, String value)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException
{
int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {
new Integer(hkey), toCstr(key), new Integer(KEY_ALL_ACCESS) });

regSetValueEx.invoke(root,
new Object[] {
new Integer(handles[0]), toCstr(valueName), toCstr(value)
});
regCloseKey.invoke(root, new Object[] { new Integer(handles[0]) });
}

// utility
private static byte[] toCstr(String str) {
byte[] result = new byte[str.length() + 1];

for (int i = 0; i < str.length(); i++) {


result[i] = (byte) str.charAt(i);
}
result[str.length()] = 0;
return result;
}
}

How to use it :

package com.rgagnon.howto;

public class WinRegistryTest {


public static void main(String args[]) throws Exception {
String value = "";

// IE Download directory (HKEY_CURRENT_USER)


value = WinRegistry.readString(
WinRegistry.HKEY_CURRENT_USER,
"Software\\Microsoft\\Internet Explorer",
"Download Directory");
System.out.println("IE Download directory = " + value);

// Query for Acrobat Reader installation path (HKEY_LOCAL_MACHINE)


value = WinRegistry.readString(

Query/Update the Windows Registry (hack) 179


Real's HowTo PDF version

WinRegistry.HKEY_LOCAL_MACHINE,
"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\App Paths\\AcroRd32.exe",
"");
System.out.println("Acrobat Reader Path = " + value);

/*
this code is broken under win7 64 :-( 20130112

// Loop through installed JRE and print the JAVA_HOME value


// HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment
java.util.Map res1 = WinRegistry.readStringValues(
WinRegistry.HKEY_LOCAL_MACHINE,
"SOFTWARE\\Wow6432Node\\JavaSoft\\Java Runtime Environment");
System.out.println("1:" + res1.toString());
*/

// on 64bit Windows, you need Wow6432Node to access 32bit related information


// "SOFTWARE\\Wow6432Node\\Microsoft\\Windows NT\\CurrentVersion"
java.util.List res2 = WinRegistry.readStringSubKeys(
WinRegistry.HKEY_LOCAL_MACHINE,
"SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion");
System.out.println(res2.toString());

WinRegistry.createKey(
WinRegistry.HKEY_CURRENT_USER, "SOFTWARE\\rgagnon.com");
WinRegistry.writeStringValue(
WinRegistry.HKEY_CURRENT_USER,
"SOFTWARE\\rgagnon.com",
"HowTo",
"java");

// WinRegistry.deleteValue(
// WinRegistry.HKEY_CURRENT_USER,
// "SOFTWARE\\rgagnon.com", "HowTo");
// WinRegistry.deleteKey(
// WinRegistry.HKEY_CURRENT_USER,
// "SOFTWARE\\rgagnon.com\\");

System.out.println("Done." );
}
}

The output :

IE Download directory = C:\Documents and Settings\Réal\Bureau


Acrobat Reader Path = C:\Program Files\Adobe\Acrobat 5.0\Reader\AcroRd32.exe
{SubVersionNumber=, CurrentBuild=1.511.1 () (snipped)...
[Accessibility, AeDebug, Asr, Classes, Compatibility, (snipped)...
Done.

Query/Update the Windows Registry (hack) 180


Real's HowTo PDF version

Quickly retrieve available Java JVM on a workstation (Windows)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0525.html

Using regedit

Use regedit utility to query the Windows registry, the result is written into a file.

start /w regedit /e jre.txt


"HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment"

The content of jre.txt on my machine :

Windows Registry Editor Version 5.00

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment]


"CurrentVersion"="1.5"

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.4]


"JavaHome"="C:\\Program Files\\Java\\j2re1.4.1_02"
"RuntimeLib"="C:\\Program Files\\Java\\j2re1.4.1_02\\bin\\client\\jvm.dll"
"MicroVersion"="1"

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.4.1_02]


"JavaHome"="C:\\Program Files\\Java\\j2re1.4.1_02"
"MicroVersion"="1"
"RuntimeLib"="C:\\Program Files\\Java\\j2re1.4.1_02\\bin\\client\\jvm.dll"

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5]


"JavaHome"="C:\\Program Files\\Java\\jre1.5.0"
"RuntimeLib"="C:\\Program Files\\Java\\jre1.5.0\\bin\\client\\jvm.dll"
"MicroVersion"="0"

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5.0]


"JavaHome"="C:\\Program Files\\Java\\jre1.5.0"
"MicroVersion"="0"
"RuntimeLib"="C:\\Program Files\\Java\\jre1.5.0\\bin\\client\\jvm.dll"

Using a CMD file

A CMD file for Windows to display the default JRE used :

@echo off
::Find the current (most recent) Java version
start /w regedit /e reg1.txt "HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment"
type reg1.txt | find "CurrentVersion" > reg2.txt
if errorlevel 1 goto ERROR

Quickly retrieve available Java JVM on a workstation (Windows) 181


Real's HowTo PDF version

for /f "tokens=2 delims==" %%x in (reg2.txt) do set JavaTemp=%%~x


if errorlevel 1 goto ERROR
echo Java Version = %JavaTemp%
del reg1.txt
del reg2.txt

::Get the home directory of the most recent Java


start /w regedit /e reg1.txt "HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\%Ja
type reg1.txt | find "JavaHome" > reg2.txt
if errorlevel 1 goto ERROR
for /f "tokens=2 delims==" %%x in (reg2.txt) do set JavaTemp=%%~x
if errorlevel 1 goto ERROR
echo Java home path (per registry) = %JavaTemp%
del reg1.txt
del reg2.txt

pause

Output example :

C:\temp>findjava.cmd
Java Version = 1.6
Java home path (per registry) = C:\\applications\\dev\\jre6

Note :
The above script returns the default JVM if the PATH variable does not override it!
Oracle client installation is famous to force an outdated Java at the beginning of the PATH. This one-liner
displays the java.exe (if any) found in the PATH :

c:\> for %i in (java.exe) do @echo. %~$PATH:i


C:\WINDOWS\system32\java.exe

The java.exe in the system32 relies on the CurrentVersion registry setting to determine which registry key to
use to look up the location of the Java RE.

Detect if a Windows service is running (capture VBS return


code)
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0575.html

You can't detect directly if Windows service is running or not in Java.

However, it's easy to do from a VBS. You execute the script from Java, wait for its completion and capture
the return code.

Obviously, this is useful only on the Windows plateform.

Detect if a Windows service is running (capture VBS return code) 182


Real's HowTo PDF version

import java.io.File;
import java.io.FileWriter;

public class VBSUtils {


private VBSUtils() { }

public static boolean isServiceRunning(String serviceName) {


try {
File file = File.createTempFile("realhowto",".vbs");
file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);

String vbs = "Set sh = CreateObject(\"Shell.Application\") \n"


+ "If sh.IsServiceRunning(\""+ serviceName +"\") Then \n"
+ " wscript.Quit(1) \n"
+ "End If \n"
+ "wscript.Quit(0) \n";
fw.write(vbs);
fw.close();
Process p = Runtime.getRuntime().exec("wscript " + file.getPath());
p.waitFor();
return (p.exitValue() == 1);
}
catch(Exception e){
e.printStackTrace();
}
return false;
}

public static void main(String[] args){


//
// DEMO
//
String result = "";
msgBox("Check if service 'Themes' is running (should be yes)");
result = isServiceRunning("Themes") ? "" : " NOT ";
msgBox("service 'Themes' is " + result + " running ");

msgBox("Check if service 'foo' is running (should be no)");


result = isServiceRunning("foo") ? "" : " NOT ";
msgBox("service 'foo' is " + result + " running ");
}

public static void msgBox(String msg) {


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, msg, "VBSUtils", javax.swing.JOptionPane.DEFAULT_OPTION);
}
}

Detect if a Windows service is running (capture VBS return code) 183


Real's HowTo PDF version

List currently running processes (Windows)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0593.html

Using TASKLIST.EXE

The Microsoft TASKLIST.EXE is used to dump the list of the currently running processes. It is similar to
tasklist window but for the console.

From a Java program, we are launching TASKLIST.EXE and capture its output.

Note : TASKLIST.EXE is not included the HOME edition of XP. But you can download it from Web, for
example : http://www.computerhope.com/download/winxp.htm.

import java.io.*;
import java.util.*;

public class WindowsUtils {


public static List<String> listRunningProcesses() {
List<String> processes = new ArrayList<String>();
try {
String line;
Process p = Runtime.getRuntime().exec("tasklist.exe /fo csv /nh");
BufferedReader input = new BufferedReader
(new InputStreamReader(p.getInputStream()));
while ((line = input.readLine()) != null) {
if (!line.trim().equals("")) {
// keep only the process name
line = line.substring(1);
processes.add(line.substring(0, line.indexOf(""")));
}

}
input.close();
}
catch (Exception err) {
err.printStackTrace();
}
return processes;
}

public static void main(String[] args){


List<String> processes = listRunningProcesses();
String result = "";

// display the result


Iterator<String> it = processes.iterator();
int i = 0;

List currently running processes (Windows) 184


Real's HowTo PDF version

while (it.hasNext()) {
result += it.next() +",";
i++;
if (i==10) {
result += "\n";
i = 0;
}
}
msgBox("Running processes : " + result);
}

public static void msgBox(String msg) {


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, msg, "WindowsUtils", javax.swing.JOptionPane.DEFAULT_OPTION);
}
}

Thanks to M. Korbel

Using a VBS

Another technique to build the required VBScript on-the-fly, execute it and capture its output.

import java.io.BufferedReader;
import java.io.File;
import java.io.FileWriter;
import java.io.InputStreamReader;
import java.util.*;

public class VBSUtils {


private VBSUtils() { }

public static List<String> listRunningProcesses() {


List<String> processList = new ArrayList<String>();
try {

File file = File.createTempFile("realhowto",".vbs");


file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);

String vbs = "Set WshShell = WScript.CreateObject(\"WScript.Shell\")\n"


+ "Set locator = CreateObject(\"WbemScripting.SWbemLocator\")\n"
+ "Set service = locator.ConnectServer()\n"
+ "Set processes = service.ExecQuery _\n"
+ " (\"select name from Win32_Process\")\n"
+ "For Each process in processes\n"
+ "wscript.echo process.Name \n"
+ "Next\n"
+ "Set WSHShell = Nothing\n";

fw.write(vbs);
fw.close();
Process p = Runtime.getRuntime().exec("cscript //NoLogo " + file.getPath());
BufferedReader input =

List currently running processes (Windows) 185


Real's HowTo PDF version

new BufferedReader
(new InputStreamReader(p.getInputStream()));
String line;
while ((line = input.readLine()) != null) {
processList.add(line);
}
input.close();
}
catch(Exception e){
e.printStackTrace();
}
return processList;
}

public static void main(String[] args){


List<String> processes = VBSUtils.listRunningProcesses();
String result = "";

Iterator<String> it = processes.iterator();
int i = 0;
while (it.hasNext()) {
result += it.next() +",";
i++;
if (i==10) {
result += "\n";
i = 0;
}
}
msgBox("Running processes : " + result);
}

public static void msgBox(String msg) {


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, msg, "VBSUtils", javax.swing.JOptionPane.DEFAULT_OPTION);
}
}

See this HowTo to check for a specific application is running or not.

Check if a program or process is running (Windows)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0610.html

Based on this HowTo which list the currently running processes, we adapt it to check for a specific program
name.

In this example, we check if the text editor TextPad.exe is running.

import java.io.BufferedReader;

Check if a program or process is running (Windows) 186


Real's HowTo PDF version

import java.io.File;
import java.io.FileWriter;
import java.io.InputStreamReader;

public class VBSUtils {


private VBSUtils() { }

public static boolean isRunning(String process) {


boolean found = false;
try {
File file = File.createTempFile("realhowto",".vbs");
file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);

String vbs = "Set WshShell = WScript.CreateObject(\"WScript.Shell\")\n"


+ "Set locator = CreateObject(\"WbemScripting.SWbemLocator\")\n"
+ "Set service = locator.ConnectServer()\n"
+ "Set processes = service.ExecQuery _\n"
+ " (\"select * from Win32_Process where name='" + process +"'\")\n"
+ "For Each process in processes\n"
+ "wscript.echo process.Name \n"
+ "Next\n"
+ "Set WSHShell = Nothing\n";

fw.write(vbs);
fw.close();
Process p = Runtime.getRuntime().exec("cscript //NoLogo " + file.getPath());
BufferedReader input =
new BufferedReader
(new InputStreamReader(p.getInputStream()));
String line;
line = input.readLine();
if (line != null) {
if (line.equals(process)) {
found = true;
}
}
input.close();

}
catch(Exception e){
e.printStackTrace();
}
return found;
}

public static void main(String[] args){


boolean result = VBSUtils.isRunning("TextPad.exe");

msgBox("Is TextPad running ? " + (result ? " Yes" : "No"));


}

public static void msgBox(String msg) {


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)

Check if a program or process is running (Windows) 187


Real's HowTo PDF version

null, msg, "VBSUtils", javax.swing.JOptionPane.DEFAULT_OPTION);


}
}

See also this HowTo

Check if a process is running (Windows) using WMIC


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../gp/windows-detect-if-a-process-is-running.html

WMIC is a powerful Windows utility. You can use to know if a particular process is running or not.

This example detects if a Tomcat instance (can be anything, ex: Apache or Excel) is running from a batch file.

@echo off
wmic process list brief | find /i "tomcat.exe"
set result=%ERRORLEVEL%
if "%result%"=="1" echo "not running"
if "%result%"=="0" echo "running"

/i is to make the find operation case-insensitive.

For Java code :

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.List;

public class WindowsUtils {


private WindowsUtils() {}
public static boolean isProcessRunning(String processName) throws IOException {
InputStream is = null;
InputStreamReader isr = null;
BufferedReader br = null;

List<String> command = new ArrayList<String>();


command.add("WMIC");
command.add("process");
command.add("list");
command.add("brief");

try {
ProcessBuilder builder = new ProcessBuilder(command);
Process process = builder.start();
is = process.getInputStream();

Check if a process is running (Windows) using WMIC 188


Real's HowTo PDF version

isr = new InputStreamReader(is);


br = new BufferedReader(isr);
String line;
processName = processName.toUpperCase();
while ((line = br.readLine()) != null) {
if (line.toUpperCase().indexOf(processName) > -1) return true;
}
return false;
}
finally {
if (br != null) br.close();
if (isr != null) isr.close();
if (is != null) is.close();
}
}

public static void main(String[] args) throws IOException {


System.out.println(WindowsUtils2.isProcessRunning("excel.exe"));
}
}

See also this HowTo.

Windows registry vs Java JDK/JRE installation


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0604.html

The JDK itself does not use the windows registry to run.

It is the JRE that uses the system registry to run in some situations like an Applet or a program started with
the WebStart technolgy.

Finally, the JRE will only use the registry if it is run from the Windows system directory (ex .
C:/winnt/system32/java.exe). This would happen if the user just types "java" on the commandline in some
random directory, because the system directory is always in the user's path. In this situation, the java.exe will
locate the current Java installation by looking at the registry key

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\CurrentVersion]

and then get the path of the JRE from the corresponding key

[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Runtime Environment\1.5\JavaHome]

Beware that some software (eg. Oracle) installs themself at the beginning of the PATH definition, so it's their
Java installation that will be found first.

Windows registry vs Java JDK/JRE installation 189


Real's HowTo PDF version

You can run the absolute path to the java.exe file, as in

"C:\Program Files\Java\jre1.5.0\bin\java.exe" MyClass

It will not use the registry, and it will be guaranteed to use jre1.5.0.

So for a regular Java SE program, it is safe to specify the complete path to the JRE to launch it.

But for the Applet/Plugin or WebStart-based programs, the registry is always used to determine the current
JRE.

Get the current Java version from a BAT file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0642.html

This command file queries the registry to find out the path of the current JRE installation and then launch it to
display the version found .

[j.cmd Win7 or better version]

@echo off
cls
setlocal ENABLEEXTENSIONS
set KEY_NAME="HKLM\SOFTWARE\JavaSoft\Java Runtime Environment"
set VALUE_NAME=CurrentVersion
::
:: get the current version
::
FOR /F "usebackq skip=2 tokens=3" %%A IN (`REG QUERY %KEY_NAME% /v %VALUE_NAME% 2^>nul`) DO (
set ValueValue=%%A
)
if defined ValueValue (
@echo the current Java runtime is %ValueValue%
) else (
@echo %KEY_NAME%\%VALUE_NAME% not found.
goto end
)
set JAVA_CURRENT="HKLM\SOFTWARE\JavaSoft\Java Runtime Environment\%ValueValue%"
set JAVA_HOME=JavaHome
::
:: get the javahome
::
FOR /F "usebackq skip=2 tokens=3*" %%A IN (`REG QUERY %JAVA_CURRENT% /v %JAVA_HOME% 2^>nul`) DO
set JAVA_PATH=%%A %%B
)
echo the path of the current Java JVM according to the registry is
echo %JAVA_PATH%

Get the current Java version from a BAT file 190


Real's HowTo PDF version

echo.
echo now if we try it :
"%JAVA_PATH%\bin\java.exe" -version
:end

[j.cmd XP version]

@echo off
cls
setlocal ENABLEEXTENSIONS
set KEY_NAME="HKLM\SOFTWARE\JavaSoft\Java Runtime Environment"
set VALUE_NAME=CurrentVersion

::
:: get the current version
::
FOR /F "usebackq skip=4 tokens=3" %%A IN (`REG QUERY %KEY_NAME% /v %VALUE_NAME% 2^>nul`) DO (
set ValueValue=%%A
)

if defined ValueValue (

@echo the current Java runtime is %ValueValue%


) else (
@echo %KEY_NAME%\%VALUE_NAME% not found.
goto end
)

set JAVA_CURRENT="HKLM\SOFTWARE\JavaSoft\Java Runtime Environment\%ValueValue%"


set JAVA_HOME=JavaHome

::
:: get the javahome
::
FOR /F "usebackq skip=4 tokens=3,4" %%A IN (`REG QUERY %JAVA_CURRENT% /v %JAVA_HOME% 2^>nul`) D
set JAVA_PATH=%%A %%B
)

echo the path of the current Java JVM according to the registry is
echo %JAVA_PATH%
echo.
echo now if we try it :
"%JAVA_PATH%\bin\java.exe" -version

:end

Output :

>j.cmd
the current Java runtime is 1.6
the path of the current Java JVM according to the registry is
C:\Program Files\Java\jre1.6.0_06

Get the current Java version from a BAT file 191


Real's HowTo PDF version

now if we try it :
java version "1.6.0_06"
Java(TM) SE Runtime Environment (build 1.6.0_06-b02)
Java HotSpot(TM) Client VM (build 10.0-b22, mixed mode, sharing)

To check a Java 32-bit installation on a 64-bit OS then change


HKLM\SOFTWARE\JavaSoft\Java Runtime Environment\...
for
HKLM\SOFTWARE\Wow6432Node\JavaSoft\Java Runtime Environment\...

Get the Windows "My Documents" path


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0572.html

This value is stored in the registry and there is no easy way to get it with regular Java unless you execute an
external utility, see this HowTo.

As an alternative, we can use a method provided by the JFileChooser class.

import javax.swing.JFileChooser;
javax.swing.filechooser.FileSystemView;

public class GetMyDocuments {


public static void main(String args[]) {
JFileChooser fr = new JFileChooser();
FileSystemView fw = fr.getFileSystemView();
System.out.println(fw.getDefaultDirectory());
}
}

See also Get Windows Special Folders (JNA)

Get the Windows Desktop path


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0652.html

import java.io.*;

public class WindowsUtils {


private static final String REGQUERY_UTIL = "reg query ";
private static final String REGSTR_TOKEN = "REG_SZ";
private static final String DESKTOP_FOLDER_CMD = REGQUERY_UTIL +
"\"HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\"

Get the Windows "My Documents" path 192


Real's HowTo PDF version

+ "Explorer\\Shell Folders\" /v DESKTOP";

private WindowsUtils() {}

public static String getCurrentUserDesktopPath() {


try {
Process process = Runtime.getRuntime().exec(DESKTOP_FOLDER_CMD);
StreamReader reader = new StreamReader(process.getInputStream());

reader.start();
process.waitFor();
reader.join();

String result = reader.getResult();


int p = result.indexOf(REGSTR_TOKEN);

if (p == -1)
return null;

return result.substring(p + REGSTR_TOKEN.length()).trim();


}
catch (Exception e) {
return null;
}
}

/**
* @param args
*/
public static void main(String[] args) {
System.out.println("Desktop directory : "
+ getCurrentUserDesktopPath());

static class StreamReader extends Thread {


private InputStream is;
private StringWriter sw;

StreamReader(InputStream is) {
this.is = is;
sw = new StringWriter();
}

public void run() {


try {
int c;
while ((c = is.read()) != -1)
sw.write(c);
}
catch (IOException e) { ; }
}

Get the Windows Desktop path 193


Real's HowTo PDF version

String getResult() {
return sw.toString();
}
}
}

See also Get Windows Special Folders (JNA)

Get the Windows Special Folders


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0653.html

import java.io.BufferedReader;
import java.io.File;
import java.io.FileWriter;
import java.io.InputStreamReader;

public class VBSUtils {

public static String SF_ALLUSERSDESKTOP = "AllUsersDesktop";


public static String SF_ALLUSERSSTARTMENU = "AllUsersStartMenu";
public static String SF_ALLUSERSPROGRAMS = "AllUsersPrograms";
public static String SF_ALLUSERSSTARTUP = "AllUsersStartup";
public static String SF_DESKTOP = "Desktop";
public static String SF_FAVORITES = "Favorites";
public static String SF_MYDOCUMENT = "MyDocuments";
public static String SF_PROGRAMS = "Programs";
public static String SF_RECENT = "Recent";
public static String SF_SENDTO = "SendTo";
public static String SF_STARTMENU = "StartMenu";
public static String SF_STARTUP = "Startup";

private VBSUtils() { }

public static String getSpecialFolder(String folder) {


String result = "";
try {
File file = File.createTempFile("realhowto",".vbs");
file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);

String vbs = "Set WshShell = WScript.CreateObject(\"WScript.Shell\")\n"


+ "wscript.echo WshShell.SpecialFolders(\"" + folder + "\")\n"
+ "Set WSHShell = Nothing\n";

fw.write(vbs);
fw.close();
Process p = Runtime.getRuntime().exec("cscript //NoLogo " + file.getPath());

Get the Windows Special Folders 194


Real's HowTo PDF version

BufferedReader input =
new BufferedReader
(new InputStreamReader(p.getInputStream()));
result = input.readLine();
input.close();
}
catch(Exception e){
e.printStackTrace();
}
return result;
}

public static void main(String[] args){


System.out.println(VBSUtils.getSpecialFolder(VBSUtils.SF_ALLUSERSDESKTOP));
System.out.println(VBSUtils.getSpecialFolder(VBSUtils.SF_DESKTOP));
System.out.println(VBSUtils.getSpecialFolder(VBSUtils.SF_PROGRAMS));
}
}

See also :
Get Windows Desktop path using the registry
Get Windows "My Documents" path using FileSystemView.getDefaultDirectory()

See also Get Windows Special Folders (JNA)

Create an Internet Shortcut


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0660.html

import java.io.*;

public class WindowsUtils {

private WindowsUtils() { }

// see note
private static final String WINDOWS_DESKTOP = "Desktop";

/**
* the current user desktop path
* @return the current user desktop path
*/
public static String getWindowsCurrentUserDesktopPath() {
return System.getenv("userprofile") + "/" + WINDOWS_DESKTOP ;
}

/**
* Create an Internet shortcut on User's Desktop no icon specified

Create an Internet Shortcut 195


Real's HowTo PDF version

* @param name name of the shortcut


* @param target URL
* @throws IOException
*/
public static void createInternetShortcutOnDesktop(String name, String target)
throws IOException
{
String path = getWindowsCurrentUserDesktopPath() + "/"+ name + ".URL";
createInternetShortcut(name, path, target, "");
}

/**
* Create an Internet shortcut on User's Desktop, icon specified
* @param name name of the shortcut
* @param target URL
* @param icon URL (ex. http://www.server.com/favicon.ico)
* @throws IOException
*/
public static void createInternetShortcutOnDesktop
(String name, String target, String icon)
throws IOException
{
String path = getWindowsCurrentUserDesktopPath() + "/"+ name + ".URL";
createInternetShortcut(name, path, target, icon);
}

/**
* Create an Internet shortcut
* @param name name of the shortcut
* @param where location of the shortcut
* @param target URL
* @param icon URL (ex. http://www.server.com/favicon.ico)
* @throws IOException
*/
public static void createInternetShortcut
(String name, String where, String target, String icon)
throws IOException
{
FileWriter fw = new FileWriter(where);
fw.write("[InternetShortcut]\n");
fw.write("URL=" + target + "\n");
if (!icon.equals("")) {
fw.write("IconFile=" + icon + "\n");
}
fw.flush();
fw.close();
}

/**
* @param args
*/
public static void main(String[] args) throws IOException {
WindowsUtils.createInternetShortcutOnDesktop
("GOOGLE", "http://www.google.com");

Create an Internet Shortcut 196


Real's HowTo PDF version

}
}

NOTE:
Prior Vista, the desktop path for a localized Windows can be different. With an english version, it's Desktop
while for a french version, it's called Bureau.

The only way to get the right name is to ask the Registry, see this HowTo.

Detect if running in remote session (Windows)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-detect-remote-session.html

[Windows only]
To detect if an application is running in a Remote Desktop session, you can call the Windows API
GetSystemMetrics. The GetSystemMetrics() function will return a non-zero value with a
SM_REMOTESESSION parameter value if the application is associated with a client terminal session.

It is useful to detect if running in a remote session to optimize visual effects or colors.

In Java, you need to use JNI (Java Native Interface) to call this Windows native API. Native Call is an Open
Source project which provide an easy way to that.

http://johannburkard.de/software/nativecall/

All you need is 2 jars (nativecall-0,4,1.jar and nativeloader-200505172341.jar) plus 1 DLL (NativeCall.dll) in
your classpath.

When running from Eclipse, the DLL should be in the bin directory of your application.

import java.io.IOException;
import com.eaio.nativecall.IntCall;
import com.eaio.nativecall.NativeCall;

public class WindowsUtils {

public static final int SM_REMOTESESSION = 4096; // remote session

private WindowsUtils() {}

public static boolean isRemote() throws SecurityException, UnsatisfiedLinkError,


UnsupportedOperationException, IOException
{
NativeCall.init();
IntCall ic = null;
try {

Detect if running in remote session (Windows) 197


Real's HowTo PDF version

ic = new IntCall("user32", "GetSystemMetrics");


int rc = ic.executeCall(new Integer(SM_REMOTESESSION));
return (rc gt; 0);
}
finally {
if (ic != null) ic.destroy();
}
}

public static void main(String ... args) throws Exception {


System.out.println(WindowsUtils.isRemote());
}
}

An easy way is to check the Windows environment variable sessionname. The value of this environment
variable will be 'Console' for a normal, local session. For an Remote Desktop session it will contain the phrase
'RDP'.

public static boolean isRemoteDesktopSession() {


System.getenv("sessionname").toLowerCase().startsWith("rdp");
}

Note that environment varialbe values are read at the JVM startup. So if the JVM process was started by a
console session, but then accessed by an RDP session, further calls to System.getenv("sessionname") still
return 'Console'

See this HowTo to detect a Citrix session.

Detect if running in a Citrix session (Windows)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-detect-if-running-in-citrix-session.html

The easiest way is to query the environment variable SESSIONNAME. The value starts with ICA... in a Citrix
session, RDP if in remote desktop session or Console if directly on a workstation.

public static boolean isRemoteDesktopSession() {


System.getenv("sessionname").toLowerCase().startsWith("rdp");
}

public static boolean isCitrixSession() {


System.getenv("sessionname").toLowerCase().startsWith("ica");
}

public static boolean isConsoleSession() {


System.getenv("sessionname").toLowerCase().startsWith("console");
}

Detect if running in a Citrix session (Windows) 198


Real's HowTo PDF version

Create a Taglet to document database access (Javadoc)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0473.html

Since JDK1.4, it is possible to create a taglet to be used with javadoc to customized the generated
documentation.

This example implements a new javadoc tag to document which tables a class is dealing with. If a method
interact with 2 tables, employee and address, then the javadoc tag

/**
*@table employee:firstname,lastname;address:city,country
* @return value
*/
public String newMethod() {
return "yo";
}

will be documented as

newMethod

public java.lang.String newMethod()

Returns:
value
Table(s):
employee address
firstname city
lastname country

The "table" taglet source

/*
* Table.java
*/

package com.rgagnon.taglet;
import com.sun.tools.doclets.Taglet;
import com.sun.javadoc.*;
import java.util.Map;
/**
* This is a taglet to document tables and fields used by a classes
* example : @table employee:lastname,firstname;address:city,country

Create a Taglet to document database access (Javadoc) 199


Real's HowTo PDF version

*
* @author Réal Gagnon
*/
public class Table implements Taglet{

private static final String NAME = "table";


private static final String HEADER = "Table(s):";

/**
* Return the name of this custom tag.
*/
public String getName() {
return NAME;
}

/**
* Will return true since <code>@todo</code>
* can be used in field documentation.
* @return true since <code>@todo</code>
* can be used in field documentation and false
* otherwise.
*/
public boolean inField() {
return false;
}

/**
* Will return true since <code>@todo</code>
* can be used in constructor documentation.
* @return true since <code>@todo</code>
* can be used in constructor documentation and false
* otherwise.
*/
public boolean inConstructor() {
return true;
}

/**
* Will return true since <code>@todo</code>
* can be used in method documentation.
* @return true since <code>@todo</code>
* can be used in method documentation and false
* otherwise.
*/
public boolean inMethod() {
return true;
}

/**
* Will return true since <code>@todo</code>
* can be used in method documentation.
* @return true since <code>@todo</code>
* can be used in overview documentation and false
* otherwise.

Create a Taglet to document database access (Javadoc) 200


Real's HowTo PDF version

*/
public boolean inOverview() {
return true;
}

/**
* Will return true since <code>@todo</code>
* can be used in package documentation.
* @return true since <code>@todo</code>
* can be used in package documentation and false
* otherwise.
*/
public boolean inPackage() {
return true;
}

/**
* Will return true since <code>@todo</code>
* can be used in type documentation (classes or interfaces).
* @return true since <code>@todo</code>
* can be used in type documentation and false
* otherwise.
*/
public boolean inType() {
return true;
}

/**
* Will return false since <code>@todo</code>
* is not an inline tag.
* @return false since <code>@todo</code>
* is not an inline tag.
*/

public boolean isInlineTag() {


return false;
}

/**
* Register this Taglet.
* @param tagletMap the map to register this tag to.
*/
public static void register(Map tagletMap) {
Table tag = new Table();
Taglet t = (Taglet) tagletMap.get(tag.getName());
if (t != null) {
tagletMap.remove(tag.getName());
}
tagletMap.put(tag.getName(), tag);
}

/**
* Given the <code>Tag</code> representation of this custom
* tag, return its string representation.

Create a Taglet to document database access (Javadoc) 201


Real's HowTo PDF version

* @param tag the <code>Tag</code> representation of this custom tag.


*/
public String toString(Tag tag) {
String output = "";
String tables [] = tag.text().split(";");
int j = tables.length;
if (j > 0) {
output = "<DT><B>" + HEADER
+ "</B><DD><TABLE><TR>";
for (int i=0; i < j ; i++){
// deals with the current table and its fields
String current[] = tables[i].split(":");
output +=
"<TD><TABLE style=\"border-style:solid;"
+ " border-width:thin\">";
output +=
"<TH ALIGN=\"center\" STYLE=\"border-style:solid;"
+ " border-width:thin\">"
+ current[0] + "</TH>";
if (current.length > 1) {
String fields[] = current[1].split(",");
int k = fields.length;
for (int n=0; n < k ; n++) {
output += "<TR><TD ALIGN=\"center\">"
+ fields[n] + "</TD></TR>";
}
}
output += "</TABLE>";
}
output += "</TR></TABLE>";
}
return output;
}

/**
* Given an array of Tags representing this custom
* tag, return its string representation.
* @param tags the array of Tags representing of this custom tag.
*/
public String toString(Tag[] tags) {
if (tags.length == 0) {
return null;
}
String result = "";
for (int i = 0; i < tags.length; i++) {
result += toString(tags[i]);
}
return result ;
}
}

Compile your taglet. Use javac compiler version 1.4.0 (or later) in the Java 2 SDK. The required class files are
in the lib\tools.jar file in the SDK. Assuming the SDK is installed at C:\Program Files\j2sdk1.4.1 :

Create a Taglet to document database access (Javadoc) 202


Real's HowTo PDF version

javac -classpath "C:\Program Files\j2sdk1.4.1\lib\tools.jar"


com\rgagnon\taglet\Table.java

Run the javadoc tool using the -taglet and -tagletpath options. For example, if your taglet class file is defined
to be in package com.rgagnon.taglet and is stored in C:\taglets\com\rgagnon\taglet\Table.class, then you
should set tagletpath to C:\taglets. This example calls javadoc on package com.package1, including Table
taglet tags:

C:\dev\Work\java\taglet>javadoc -taglet com.rgagnon.taglet.Table


-tagletpath c:\dev\work\java\taglet com.package1

Download this taglet here.

Generate the Javadoc "en français"


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0437.html

The javadoc utility uses the regular Java mechanism to internationalize its output. The tools.jar in the lib
directory contains the resource bundle standard.properties used by Javadoc to generated the labels. To add a
new language, you need to create the appropriate resource bundle, in our case for french, we need a file called
standard_fr.properties.

The new file must be in the package com.sun.tools.doclets.standard.resources.

Extract from tools.jar, the standard.properties files (keep the directory structure). Copy it under the name
standard_fr.properties. Translate it (or you can download my "incomplete" version here).

[standard.properties (extract)]

doclet.Window_Split_Index={0}\: {1}-Index
doclet.Packages=Packages
doclet.SerialData=Serial Data\:
doclet.Since=Since\:
doclet.Warn_inline_taglet=Inline tag {0} should only be used with a {1}.
doclet.ClassUse_Subinterface=Subinterfaces of {0} in {1}
doclet.Frame_Version=Frame version
doclet.Generated_Docs_Untitled=Generated Documentation (Untitled)

[standard_fr.properties (extract)]

doclet.Window_Split_Index={0}\: {1}-Index
doclet.Packages=Paquetages
doclet.SerialData=Donn\u00E9e s\u00E9rialis\u00E9e\:
doclet.Since=Depuis\:
doclet.Warn_inline_taglet=Inline tag {0} should only be used with a {1}.
doclet.ClassUse_Subinterface=Sous-interfaces de {0} dans {1}

Generate the Javadoc "en français" 203


Real's HowTo PDF version

doclet.Frame_Version=Version avec cadres


doclet.Generated_Docs_Untitled=Documentation g\u00E9n\u00E9r\u00E9e

Once everything translated, put your standard_fr.properties into the tools.jar making sure that the file is
located in the right package (along standard.properties in com.sun.tools.doclets.standard.resources).

To generate in french, use the -locale switch on the command line

javadoc -locale fr ....

NOTE : Make sure the -locale switch is the first one.

Using Ant,

<javadoc
locale="fr"
sourcefiles="c:/client/Client.java"
destdir="javadoc/Client"
author="true"
version="true"
use="true"
private="true"
windowtitle="Client">
<doctitle><![CDATA[<h1>Client</h1>]]></doctitle>
<bottom><![CDATA[<i>Copyright &#169; 2003 Real's Howto.</i>]]></bottom>
</javadoc>

Document a package using Javadoc


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0502.html

Suppose I have a package called com.rgagnon with one HelloWorld class.

com
rgagnon
HelloWorld.java

In the directory containing HelloWorld.java, add a file called package.html.

This must be a complete HTML file (with HEAD and BODY). the first line of the body will be used a the
package description by javadoc.

<html><head></head><body>
this is <i>com.rgagnon</i> package description,
see <a href="http://www.rgagnon.com" target="_top">web site</a>
</body></html>

Document a package using Javadoc 204


Real's HowTo PDF version

Now execute the javadoc utility located in [JDK]\bin directory from the root of the com.rgagnon package.

\progra~1\Java\jdk1.5.0\bin\javadoc -d javadoc0 -linksource com.rgagnon

where -d javadoc0 is used to specify the output directory and


-linksource to create HTML version of the source file.

See the result.

Since JDK 1.5, to create a package comment file, you have a choice of two files to place your comments:

• package-info.java - Can contain a package declaration, package annotations, package comments and
Javadoc tags. This file is new in JDK 5.0, and is preferred over package.html.
• package.html - Can contain only package comments and Javadoc tags, no package annotations.

See http://java.sun.com/j2se/1.5.0/docs/tooldocs/windows/javadoc.html#packagecomment

Display a comment in a Javadoc


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0615.html

Use the numerical identity to represent the / in the javadoc section to avoid any conflict with a real comment.

import java.awt.*;
public class Example {
/**
* Simple Frame
* <pre>
* &#47;* create a frame *&#47;
* Frame f = new Frame()
* </pre>
* @param args
*/
public static void main(String args[]){
Frame f = new Frame();
f.setSize(200,200);
f.setVisible(true);
}
}

and the javadoc output is :

Display a comment in a Javadoc 205


Real's HowTo PDF version

You can represent any character with a numerical identity, the syntax is &#nnn; where nnn is the Unicode
code (decimal value) of the character.

Display XML in a Javadoc


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0623.html

Let's say you have a comment like this

/**
* To use this class use this XML
*
* <xml>
* <parameter>foo</parameter>
* <value>bar</value>
* </xml>
*
*/

The XML will not be visible since it will embedded in the HTML as tag and not as text.

With Javadoc 1.5, you can use the {@code ... } command. :

/**
* To use this class use this XML
* <pre>
* {@code

Display XML in a Javadoc 206


Real's HowTo PDF version

* <xml>
* <parameter>foo</parameter>
* <value>bar</value>
* </xml>
* }
* </pre>
*/

With the previous versions, one way was to add a space after the <.

/**
* To use this class use this XML
* <pre>
* < xml>
* < parameter>foo< /parameter>
* < value>bar< /value>
* < /xml>
* }
* </pre>
*/

Add a copyright notice to a Javadoc


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0626.html

Use the -bottom parameter to the javadoc command line.

-bottom '<font size="-1"><a href="http://www.rgagnon.com">Real&apos;s HowTo</a>


<br>&copy; 2008 rgagnon.com</font>'

The result looks like this :

Use a Log file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0501.html

Since 1.4, a logging functionnality is included with the JDK. It's the java.util.logging package.

Add a copyright notice to a Javadoc 207


Real's HowTo PDF version

import java.util.logging.*;
import java.io.*;

public class TestLog {

public static Logger logger;

static {
try {
boolean append = true;
FileHandler fh = new FileHandler("TestLog.log", append);
//fh.setFormatter(new XMLFormatter());
fh.setFormatter(new SimpleFormatter());
logger = Logger.getLogger("TestLog");
logger.addHandler(fh);
}
catch (IOException e) {
e.printStackTrace();
}
}

public static void main(String args[]) {


logger.severe("my severe message");
logger.warning("my warning message");
logger.info("my info message");
}
}

and the result is

2005-02-28 21:19:28 TestLog main


GRAVE: my severe message
2005-02-28 21:19:28 TestLog main
ATTENTION: my warning message
2005-02-28 21:19:28 TestLog main
INFO: my info message

if the XMLFormatter is in use then the output is

<?xml version="1.0" encoding="windows-1252" standalone="no"?>


<!DOCTYPE log SYSTEM "logger.dtd">
<log>
<record>
<date>2005-02-28T21:21:09</date>
<millis>1109643669250</millis>
<sequence>0</sequence>
<logger>TestLog</logger>
<level>SEVERE</level>
<class>TestLog</class>
<method>main</method>
<thread>10</thread>
<message>my severe message</message>
</record>

Use a Log file 208


Real's HowTo PDF version

<record>
<date>2005-02-28T21:21:09</date>
<millis>1109643669328</millis>
<sequence>1</sequence>
<logger>TestLog</logger>
<level>WARNING</level>
<class>TestLog</class>
<method>main</method>
<thread>10</thread>
<message>my warning message</message>
</record>
<record>
<date>2005-02-28T21:21:09</date>
<millis>1109643669328</millis>
<sequence>2</sequence>
<logger>TestLog</logger>
<level>INFO</level>
<class>TestLog</class>
<method>main</method>
<thread>10</thread>
<message>my info message</message>
</record>
</log>

to customize the output, you can provide you own formatter

import java.util.logging.*;
import java.io.*;

public class TestLog {

public static Logger logger;

static {
try {
boolean append = true;
FileHandler fh = new FileHandler("TestLog.log", append);
fh.setFormatter(new Formatter() {
public String format(LogRecord rec) {
StringBuffer buf = new StringBuffer(1000);
buf.append(new java.util.Date());
buf.append(' ');
buf.append(rec.getLevel());
buf.append(' ');
buf.append(formatMessage(rec));
buf.append('\n');
return buf.toString();
}
});
logger = Logger.getLogger("TestLog");
logger.addHandler(fh);
}
catch (IOException e) {
e.printStackTrace();

Use a Log file 209


Real's HowTo PDF version

}
}

public static void main(String args[]) {


logger.severe("my severe message");
logger.warning("my warning message");
logger.info("my info message");
}
}

then the output is

Mon Feb 28 21:30:54 EST 2005 SEVERE my severe message


Mon Feb 28 21:30:54 EST 2005 WARNING my warning message
Mon Feb 28 21:30:54 EST 2005 INFO my info message

To limit the log file size and set a rolling pattern

int limit = 1000000; // 1 Mb


int numLogFiles = 3;
FileHandler fh = new FileHandler("TestLog%g.log", limit, numLogFiles);

will give TestLog0.log, TestLog1.log and so on.

Default values are defined in JRE_HOME/lib/logging.properties. To use a different properties file, you
specify a filename with the java.util.logging.config.file system property.

java -Djava.util.logging.config.file=mylogging.props TestLog

To suppress the logging output to the console


Logger rootLogger = Logger.getLogger("");
Handler[] handlers = rootLogger.getHandlers();
if (handlers[0] instanceof ConsoleHandler) {
rootLogger.removeHandler(handlers[0]);
}

or modify the logging.properties file located in JRE_HOME/lib (default).

Look for the property handlers and remove the value java.util.logging.ConsoleHandler

You may want to take a look at another popular logging mechanism : Log4J.

See also this HowTo and this one

Trace the execution


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0301.html

Trace the execution 210


Real's HowTo PDF version

JDK1.5+

Generate a StackTrace and then parse the StackTraceElements.

[LogUtils.java]

public class LogUtils {

private static final String NEWLINE = System.getProperty("line.separator");

private LogUtils (){ }

public static String getStack(int deep) {


// deep = 0 no level, only current calling method
// n from "n" levels
StringBuilder sb = new StringBuilder();
StackTraceElement ste [] = Thread.currentThread().getStackTrace();
int k = 2; // startingpoint 0:getstacktrace() 1: getStack()
int j = ste.length - 1;
// process the stack
if (deep > j) deep = j;
else deep = deep + k;

while (k <= deep) {


String line = ste[k].toString();
sb.append(line + NEWLINE);
k++;
}
return sb.toString();
}

public static void main(String args[]){


Test test = new Test();
test.doit();
}
}

class Test {
public void doit() {
System.out.println("*Howto Trace only 1 level\n" + LogUtils.getStack(1));
System.out.println("*Howto Trace only 10 levels\n" + LogUtils.getStack(10));
System.out.println("*Howto Trace no level (current)\n" + LogUtils.getStack(0));
}
}

And the output should be

*Howto Trace only 1 level


Test.doit(LogUtils.java:35)
LogUtils.main(LogUtils.java:29)

Trace the execution 211


Real's HowTo PDF version

*Howto Trace only 10 levels


Test.doit(LogUtils.java:36)
LogUtils.main(LogUtils.java:29)

*Howto Trace no level (current)


Test.doit(LogUtils.java:37)

See also this Howto


• Get the current or calling method name.

Time the execution


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0132.html

public class ExecutionTimer {


private long start;
private long end;

public ExecutionTimer() {
reset();
}

public void start() {


start = System.currentTimeMillis();
}

public void end() {


end = System.currentTimeMillis();
}

public long duration(){


return (end-start);
}

public void reset() {


start = 0;
end = 0;
}

public static void main(String s[]) {


// simple example
ExecutionTimer t = new ExecutionTimer();
t.start();
for (int i=0; i < 80; i++){ System.out.print(".");}
t.end();
System.out.println("\n" + t.duration() + " ms");
}
}

Time the execution 212


Real's HowTo PDF version

See this HowTo to format a duration in ms into a string as "Days , Hours , minutes and seconds".

Log information efficiently (with Log4J)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0527.html

In production code, a good practice is to only log what is necessary in the context.

With Log4J, you can have different levels of message written into your log.

public class MyClass {

/**
* Logger log4j
*/
static Logger logger = Logger.getLogger(MyClass.class.getName());

...
logger.debug("I'm here");
logger.info(e.getMessage());
logger.warning("something wrong " + e.getMessage());
logger.error("omg " + e.getMessage());
...

While you can set the level in your code with something like

logger.setLevel(Level.WARN);

it's more flexible to do it from the Log4J properties file

; can be OFF, FATAL, ERROR, WARN, INFO, DEBUG, ALL


log4j.threshold=WARN

You put the properties file in the classpath and then from your code

URL url = ClassLoader.getSystemResource("log4j.props");


PropertyConfigurator.configure(url);

Logging activities have a cost. Even if you set the level at DEBUG level, the logger.debug(...) is
interpreted. Consider this line :

logger.setLevel(Level.DEBUG);
logger.debug("something wrong with the value of " + myValue.toString());

the toString() method will be called and the result concatened to a String even if the DEBUG level is
disabled.

Log information efficiently (with Log4J) 213


Real's HowTo PDF version

The best practice is to check if the level is enabled or not.

logger.setLevel(Level.DEBUG);
if (logger.isDebugEnabled()) {
logger.debug("something wrong with the value of " + myValue.toString());
}

This way you will not incur the cost of parameter construction if debugging is disabled for logger.

You can even remove the unwanted logging operation from the bytecode! See this HowTo.

Finally it's a good idea to design a robust toString() method for your class like this one :

public String toString(){


StringBuffer sb = new StringBuffer();
sb.append(getClass().getName())
sb.append(" myValue=[").append(this.myValue).append("]");
sb.append(" anotherValue=[").append(this.anotherProperty).append("]");
return sb.toString();
}

even if myValue is null, this toString() method will display "null" as the value and not throw a
NullPointerExeception.

See also this HowTo and this one

Change the logging level on-the-fly (Log4J)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0621.html

While you can set the logging level through the configuration properties file

; can be OFF, FATAL, ERROR, WARN, INFO, DEBUG, ALL


log4j.threshold=WARN

It may be useful to change it on-the-fly for debugging purpose. You need to get the Log4J "root" Logger
and then change its "level".

...
setLogLevel("DEBUG");
...
setLogLevel("INFO");
...

private void setLogLevel(String level) {


Logger root = Logger.getRootLogger();
if ("DEBUG".equals(level)) {

Change the logging level on-the-fly (Log4J) 214


Real's HowTo PDF version

root.setLevel(org.apache.log4j.Level.DEBUG);
}
else {
root.setLevel(org.apache.log4j.Level.INFO);
}
}

Enable debug log level on OpenSource package(Apache


Commons Logging)
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-enable-debug-logging.html

Typically, Apache products are using the Apache Commons Logging.

You can enable the logging at the DEBUG level by simply setting 2 environment variable.

For example, if you have something using the Axis library to do a Web Service call, then

java.exe -Dorg.apache.commons.logging.Log=org.apache.commons.logging.impl.SimpleLog
-Dorg.apache.commons.logging.simplelog.defaultlog=debug
MyClassUsingAxis

will launch the program and output to stdout the debugging information.

[DEBUG] ProjectResourceBundle - -getBundle(org.apache.axis,org.apache.axis.i18n,resource,null


[DEBUG] ProjectResourceBundle - -loadBundle: Ignoring MissingResourceException: Can't find bu
[DEBUG] ProjectResourceBundle - -Created org.apache.axis.i18n.resource, linked to parent null
[DEBUG] ProjectResourceBundle - -getBundle(org.apache.axis,org.apache.axis.utils,resource,nul
[DEBUG] ProjectResourceBundle - -loadBundle: Ignoring MissingResourceException: Can't find bu
[DEBUG] ProjectResourceBundle - -org.apache.axis.i18n.resource::handleGetObject(setMsgForm)
[DEBUG] SOAPPart - -Setting current message form to: FORM_STRING (currentMessage is now <?xml
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http:/
<soapenv:Header>
<ns1:biBusHeader soapenv:mustUnderstand="0" xmlns:ns1="http://developer.cognos.com/schemas/
</soapenv:Header>
<soapenv:Body>
<ns2:logon soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:ns2="htt

...

[DEBUG] HTTPSender - -HTTP/1.1 405 Method Not Allowed


[DEBUG] HTTPSender - -Allow OPTIONS, TRACE, GET, HEAD
[DEBUG] HTTPSender - -Content-Length 1564
[DEBUG] HTTPSender - -Content-Type text/html
[DEBUG] HTTPSender - -Server Microsoft-IIS/6.0

...

Enable debug log level on OpenSource package(Apache Commons Logging) 215


Real's HowTo PDF version

It's possible to enable only the logging for HTTP activities.

-Dorg.apache.commons.logging.Log=org.apache.commons.logging.impl.SimpleLog
-Dorg.apache.commons.logging.simplelog.showdatetime=true
-Dorg.apache.commons.logging.simplelog.log.httpclient.wire=debug
-Dorg.apache.commons.logging.simplelog.log.org.apache.commons.httpclient=debug

2009/08/21 12:15:56:109 EDT [DEBUG] header - >> "SOAPAction: urn:GeteBayOfficialTime[\r][\n]"


2009/08/21 12:15:56:109 EDT [DEBUG] header - >> "User-Agent: Axis2[\r][\n]"
2009/08/21 12:15:56:109 EDT [DEBUG] header - >> "Host: api.sandbox.ebay.com[\r][\n]"
2009/08/21 12:15:56:109 EDT [DEBUG] header - >> "Content-Length: 1546[\r][\n]"
2009/08/21 12:15:56:109 EDT [DEBUG] header - >> "Content-Type: text/xml; charset=UTF-8[\r][\n
2009/08/21 12:15:56:109 EDT [DEBUG] header - >> "[\r][\n]"

Apache PDFBox emits a lot of infos in debug mode.

To remove the debug mode for PDFBox :

if (logger.isDebugEnabled()) {
Logger logpdfengine = Logger.getLogger("org.apache.pdfbox.util.PDFStreamEngine");
logpdfengine.setLevel(org.apache.log4j.Level.OFF);
}

Make a JAR executable


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0166.html

In the manifest file of a JAR, it is possible to specify the class to be used when the JVM is lauched with the
JAR as parameter. The class must have a main().

Try with this simple class

import java.awt.*;
import java.awt.event.*;

public class MyClass {


public static void main(String[] args) {
Frame f = new Frame();
f.addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);

Make a JAR executable 216


Real's HowTo PDF version

f.add(new Label("Hello world"));


f.setSize(200,200);
f.setVisible(true);
}
}

Then create this manifest file (manifest.mft) with any text editor.

Manifest-Version: 1.0
Main-Class: MyClass
Class-path: .

Main-Class specifies the entry point with the main(String args[]) method.

The Class-path is used to specify the dependency of this jar (if any). You add the directories and jars
separated by a space. It is important because when running a jar , the CLASSPATH definition (as defined
by the environnement variable) is overridden.

Next, you include the manifest file in the JAR (MyJar.jar) with the MyClass class.

jar cvfm myjar.jar manifest.mft *.class

Then you are able to start the MyClass.class by double-clicking on the MyJar.jar file (if the JRE is correctly
installed) or by typing

java -jar myjar.jar

If you need to pass parameters, use the -D switch before the -jar switch and use the getProperty() method to
get the value.

The file association mechanism is made during the installation of the JRE.

You can verify that everything is ok with the following command from a DOS Shell

>assoc .jar
.jar=jarfile

>ftype jarfile
jarfile="C:\Program Files\Java\jre1.5.0_10\bin\javaw.exe" -jar "%1" %*

If the association is broken or you need to change the JRE used then by using the assoc/ftype utilities, you
can modify the association easily (use /? to display the syntax of the assoc and ftype utilities).

NOTE: On WinXp (or better), your user account needs to be at the Admin level.

On Windows (NT or better), you can also make JARs run from the command-line by setting the PATHEXT
environment variable, for example
SET PATHEXT=.EXE;.BAT;.CMD;.JAR

Make a JAR executable 217


Real's HowTo PDF version

Then if you have the jar file MyJar.jar accessible via the PATH environment variable, typing "MyJar" on
the DOS command line will invoke "javaw -jar MyJar.jar" .

Application with multiples Jars


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0319.html

Supposed we have a jar called Main.jar for the application. This application needs Second.jar and Third.jar
. In the manifest file of the first jar (Main.jar), you adjust the Class-Path setting :

Manifest-Version: 1.0
Main-Class: MyClass
Class-Path: Second.jar Third.jar

The value of the Class-Path attribute specifies the relative URLs of the extensions or libraries that this
application or extension needs. URLs are separated by one or more spaces. The application or extension
class loader uses the value of this attribute to construct its internal search path.

You can use the -i option to speed up your application's class loading time:
jar -i main.jar

This will build an an INDEX.LIST file in the META-INF directory which will enable the application class
loader to download the right jar files when it is searching for classes or resources.

Extract a file from a Jar


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0429.html

The following snippet extract a file (mydb.mdb) from a jar.

import java.io.*;
import java.util.jar.*;
import java.util.zip.*;

public class ExtractFromJAR {

public void extractMyMDBromJAR(String dest){


try {
String home = getClass().getProtectionDomain().
getCodeSource().getLocation().toString().
substring(6);

Application with multiples Jars 218


Real's HowTo PDF version

JarFile jar = new JarFile(home);


ZipEntry entry = jar.getEntry("mydb.mdb");
File efile = new File(dest, entry.getName());

InputStream in =
new BufferedInputStream(jar.getInputStream(entry));
OutputStream out =
new BufferedOutputStream(new FileOutputStream(efile));
byte[] buffer = new byte[2048];
for (;;) {
int nBytes = in.read(buffer);
if (nBytes <= 0) break;
out.write(buffer, 0, nBytes);
}
out.flush();
out.close();
in.close();
}
catch (Exception e) {
e.printStackTrace();
}
}

public static void main(String args []){


new ExtractFromJAR().extractMyMDBFromJAR(".");
}

Grab this auto-run Jar if you want to try it.

To create an auto-run JAR, first create a manifest.mft

Manifest-Version: 1.0
Classpath: .\mydb.jar
Main-Class: ExtractFromJAR

Create the JAR

C:\jdk141\bin\jar cvfm mydb.jar manifest.mft ExtractFromJAR.class mydb.mdb

Run it ... and the mydb.mdb file should appear in the current directory.

java -jar mydb.jar

(A tip from Fred Hommersom) Your code reads:


String home = getClass().getProtectionDomain().
getCodeSource().getLocation().toString().substring(6);

Extract a file from a Jar 219


Real's HowTo PDF version

I got a problem when the jar file was located in C:\Program Files\xyz due to the embedded space. So I
modified the code to

String home = getClass().getProtectionDomain()


.getCodeSource().getLocation()
.getPath().replaceAll("%20", " ");

Determine if running from JAR


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0391.html

package com.rgagnon;

public class HelloClass {


public static void main(String[] args) {
new HelloClass().say();
}

public void say() {


String className = this.getClass().getName().replace('.', '/');
String classJar =
this.getClass().getResource("/" + className + ".class").toString();
if (classJar.startsWith("jar:")) {
System.out.println("*** running from jar!");
}
System.out.println(classJar);
}
}

The output

>jar cvfm Hello.jar manifest.mft com\rgagnon\HelloClass.class


added manifest
adding: com/rgagnon/HelloClass.class (in=1059) (out=601) (deflated 43%)

>java com.rgagnon.HelloClass
file:/C:/DEV/WORK/JAVA/com/rgagnon/HelloClass.class

>java -jar Hello.jar


*** running from jar!
jar:file:/C:/DEV/WORK/JAVA/Hello.jar!/com/rgagnon/HelloClass.class

Here a variation on this subject, a method to return the name of the current running jar.

package com.rgagnon.howto;

public class RunningJar {

Determine if running from JAR 220


Real's HowTo PDF version

public static void main(String[] args) {


String runningJarName = new RunningJar().getRunningJarName();
if (runningJarName != null) {
System.out.println("Running from " + runningJarName);
}
else {
System.out.println("Not running from a jar");
}
}

public String getRunningJarName() {


String className = this.getClass().getName().replace('.', '/');
String classJar =
this.getClass().getResource("/" + className + ".class").toString();
if (classJar.startsWith("jar:")) {
String vals[] = classJar.split("/");
for (String val: vals) {
if (val.contains("!")) {
return val.substring(0, val.length() - 1);
}
}
}
return null;
}
}

/*
output :

>java -jar yop.jar


Running from yop.jar

>ren yop.jar yip.jar

>java -jar yip.jar


Running from yip.jar

*/

See these related HowTo's : Obtain from where a Class is loaded Get the "root" of an application

Get list of classes in package (in a Jar)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0513.html

import java.util.jar.*;
import java.util.*;
import java.io.*;

Get list of classes in package (in a Jar) 221


Real's HowTo PDF version

public class PackageUtils {

private static boolean debug = true;

private PackageUtils() {}

public static List getClasseNamesInPackage


(String jarName, String packageName){
ArrayList classes = new ArrayList ();

packageName = packageName.replaceAll("\\." , "/");


if (debug) System.out.println
("Jar " + jarName + " looking for " + packageName);
try{
JarInputStream jarFile = new JarInputStream
(new FileInputStream (jarName));
JarEntry jarEntry;

while(true) {
jarEntry=jarFile.getNextJarEntry ();
if(jarEntry == null){
break;
}
if((jarEntry.getName ().startsWith (packageName)) &&

(jarEntry.getName ().endsWith (".class")) ) {


if (debug) System.out.println
("Found " + jarEntry.getName().replaceAll("/", "\\."));
classes.add (jarEntry.getName().replaceAll("/", "\\."));
}
}
}
catch( Exception e){
e.printStackTrace ();
}
return classes;
}

/**
*
*/
public static void main (String[] args){
List list = PackageUtils.getClasseNamesInPackage
("C:/j2sdk1.4.1_02/lib/mail.jar", "com.sun.mail.handlers");
System.out.println(list);
/*
output :

Jar C:/j2sdk1.4.1_02/lib/mail.jar looking for com/sun/mail/handlers


Found com.sun.mail.handlers.text_html.class
Found com.sun.mail.handlers.text_plain.class
Found com.sun.mail.handlers.text_xml.class
Found com.sun.mail.handlers.image_gif.class

Get list of classes in package (in a Jar) 222


Real's HowTo PDF version

Found com.sun.mail.handlers.image_jpeg.class
Found com.sun.mail.handlers.multipart_mixed.class
Found com.sun.mail.handlers.message_rfc822.class
[com.sun.mail.handlers.text_html.class,
com.sun.mail.handlers.text_xml.class, com
.sun.mail.handlers.image_jpeg.class,
, com.sun.mail.handlers.message_rfc822.class]

*/
}
}

Add version to Jar packaging


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0388.html

Let's say we have the following class (package is mandatory)

package com.rgagnon;

public class Hello {


public static void main(String[] args) {
new Hello().say("Hello World!");
}

public void say(String s) {


System.out.println(s);
}
}

First create a MANIFEST.MF file :

Manifest-Version: 1.0
Main-Class: com.rgagnon.Hello

Then build the executable Jar and run it.

>jar cvfm hello.jar MANIFEST.MF com\rgagnon\Hello.class

>java -jar hello.jar


Hello World!

Now modify the manifest to include versioning information.

Manifest-Version: 1.0
Main-Class: com.rgagnon.Hello
Specification-Version: 2.1
Implementation-Version: 1.1

Add version to Jar packaging 223


Real's HowTo PDF version

Modify the class to display the version.

package com.rgagnon;

public class Hello {


public static void main(String[] args) {
new Hello().say("Hello World!");
}

Hello() {
Package p = this.getClass().getPackage();
System.out.println("Hello Specification Version : "
+ p.getSpecificationVersion());
System.out.println("Hello Implementation Version : "
+ p.getImplementationVersion());
}

public void say(String s) {


System.out.println(s);
}
}

Compile and rebuild the Jar and execute

> jar cvfm hello.jar MANIFEST.MF com\rgagnon\Hello.class

> java -jar hello.jar


Specification Version : 2.1
Implementation Version : 1.1
Hello World!

See also this Howto.

This example opens a given Jar and outputs its version information.

package com.rgagnon.howto;

import java.util.jar.*;

public class JarUtils {

private JarUtils() {}

public static String getJarImplementationVersion(String jar)


throws java.io.IOException
{
JarFile jarfile = new JarFile(jar);
Manifest manifest = jarfile.getManifest();
Attributes att = manifest.getMainAttributes();
return att.getValue("Implementation-Version");
}

Add version to Jar packaging 224


Real's HowTo PDF version

public static String getJarSpecificationVersion(String jar)


throws java.io.IOException
{
JarFile jarfile = new JarFile(jar);
Manifest manifest = jarfile.getManifest();
Attributes att = manifest.getMainAttributes();
return att.getValue("Specification-Version");
}
public static void main(String[] args) throws java.io.IOException{
String javaMailJar = "C:/Program Files/Java/jre1.5.0/lib/mail.jar";

System.out.println("Specification-Version: "
+ JarUtils.getJarSpecificationVersion(javaMailJar));
System.out.println("Implementation-Version: "
+ JarUtils.getJarImplementationVersion(javaMailJar));
/*
* output :
* Specification-Version: 1.3
* Implementation-Version: 1.3.1
*/
}
}

Use ANT to Build a JAR with version/build number


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0532.html

• Download ANT from http://ant.apache.org/bindownload.cgi


• Unzip into the root of C: (Windows), rename the folder to \Ant
• Create a file call antenv.cmd. Before using ANT, you must execute this file to set up the environment. You
may need to adjust the values according to your installation!
set ANT_HOME=c:\ant
set JAVA_HOME=C:\Progra~1\Java\jdk1.5.0
set PATH=%ANT_HOME%\bin;%JAVA_HOME%\bin;%path%
• Create a simple Hello class as shown below (you need have a package).
package howto;
public class Hello {
public static void main( String[] args ){
System.out.println( "Hello World" );
}
}
• Execute your antenv.cmd to set the environment
• Compile your Hello class and make a jar to check if your environment is ok.
> javac howto/Hello.java
> jar -cvf hello.jar howto/Hello.class
added manifest
adding: howto/hello.class(in = 415) (out= 284) (deflated 31%)
> java -cp hello.jar howto.Hello
Hello World

Use ANT to Build a JAR with version/build number 225


Real's HowTo PDF version

• Create a build.xml which is the default ant build file ...


• ... and load it into your favorite editor. Type the following ant script and save it.
<project default="buildHello">
<target name="compile">
<javac srcdir="." />
</target>

<target name="buildHello" depends="compile" />


</project>

Go back to the DOS shell and launch Ant with

> ant compile


Buildfile: build.xml

compile:
[javac] Compiling 1 source file
• Go back to the editor and add the jar building command. The target compile is also executed since the target
jar depends on it.
<project default="buildHello">
<target name="compile">
<javac srcdir="." />
</target>

<target name="jar" depends="compile">


<jar destfile="hello.jar"
basedir="."
includes="**/*.class"
/>
</target>

<target name="buildHello" depends="compile,jar" />


</project>
• Execute your Ant script :
> ant jar
Buildfile: build.xml

compile:

jar:
[jar] Building jar: /Dev/hello.jar

BUILD SUCCESSFUL
Total time: 2 seconds
$ jar -tvf hello.jar
jar -tvf hello.jar
0 Wed May 03 17:06:32 EST 2006 META-INF/
55 Wed May 03 17:06:32 EST 2006 META-INF/MANIFEST.MF
55 Wed May 03 17:06:32 EST 2006 howto/
335 Wed May 03 16:36:16 EST 2006 howto/Hello.class
• Try your new Jar file
> java -cp Hello.jar howto.Hello
Hello World

Use ANT to Build a JAR with version/build number 226


Real's HowTo PDF version

• Make your Jar auto-executable by specifying the Main class into a MANIFEST.MF file to be included in
the Jar. Add the following lines to build.xml
<project default="buildHello">
<target name="compile">
<javac srcdir="." />
</target>

<target name="jar" depends="compile">


<delete file="hello.jar"/>
<delete file="MANIFEST.MF"/>
<manifest file="MANIFEST.MF">
<attribute name="Built-By" value="${user.name}"/>
<attribute name="Main-Class" value="howto.Hello"/>
</manifest>

<jar destfile="hello.jar"
basedir="."
includes="**/*.class"
manifest="MANIFEST.MF"
/>
</target>

<target name="buildHello" depends="compile,jar" />


</project>
• Now you can launch Hello with only
> ant jar
...
> java -jar hello.jar
Hello World
• Add a build number with the Ant task buildnumber . Ant will create (if necessary) and increment a property
in a file called build.num (so you need to keep it!). Then a property, build.number, is available in your Ant
script. The version number is also a property. Here it is hard-coded in the script but you can read it from a
file.
<project default="buildHello">
<target name="compile">
<javac srcdir="." />
</target>

<target name="jar" depends="compile">


<delete file="hello.jar"/>
<delete file="MANIFEST.MF"/>
<property name="version.num" value="1.00"/>
<buildnumber file="build.num"/>

<manifest file="MANIFEST.MF">
<attribute name="Built-By" value="${user.name}"/>
<attribute name="Main-Class" value="howto.Hello"/>
<attribute name="Implementation-Version"
value="${version.num}-b${build.number}"/>
</manifest>

<jar destfile="hello.jar"
basedir="."

Use ANT to Build a JAR with version/build number 227


Real's HowTo PDF version

includes="**/*.class"
manifest="MANIFEST.MF"
/>
</target>

<target name="buildHello" depends="compile,jar" />


</project>
• If you examine the MANIFEST.MF, you now see a new entry
Implementation-Version: 1.00-b1
• and after the next build operation, the entry will be
Implementation-Version: 1.00-b2
• Modify the Hello class to read the Implementation-Version information and display it.
package howto;

public class Hello {


public static void main( String[] args ){
System.out.println( "Hello World ");
System.out.println("version : " +
Hello.class.getPackage().getImplementationVersion() );
}
}
• Finally we add a target to cleanup and the main target to build everything to the build.xml file.
<project default="buildHello">
<target name="compile">
<javac srcdir="." />
</target>

<target name="jar">
<delete file="hello.jar"/>
<property name="version.num" value="1.00"/>
<buildnumber file="build.num"/>

<manifest file="MANIFEST.MF">
<attribute name="Built-By" value="${user.name}"/>
<attribute name="Main-Class" value="howto.Hello"/>
<attribute name="Implementation-Version"
value="${version.num}-b${build.number}"/>
</manifest>

<jar destfile="hello.jar"
basedir="."
includes="**/*.class"
manifest="MANIFEST.MF"
/>
</target>

<target name="cleanup">
<delete>
<fileset dir="." includes="**/*.class"/>
<fileset file="MANIFEST.MF"/>
</delete>
</target>

<target name="buildHello" depends="compile,jar,cleanup" />

Use ANT to Build a JAR with version/build number 228


Real's HowTo PDF version

</project>
• Build and launch the Hello class
> ant buildHello
...
> java -jar hello.jar
Hello World
version : 1.00-b3

b3 == build #3 (if it's your third build !)

Build number is great but a Built date is useful too!

...
<target name="jar">
<delete file="hello.jar"/>
<property name="version.num" value="1.00"/>
<buildnumber file="build.num"/>
<tstamp>
<format property="TODAY" pattern="yyyy-MM-dd HH:mm:ss" />
</tstamp>

<manifest file="MANIFEST.MF">
<attribute name="Built-By" value="${user.name}"/>
<attribute name="Main-Class" value="howto.Hello"/>
<attribute name="Implementation-Version"
value="${version.num}-b${build.number}"/>
<attribute name="Built-Date" value="${TODAY}"/>
</manifest>

<jar destfile="hello.jar"
basedir="."
includes="**/*.class"
manifest="MANIFEST.MF"
/>
</target>

See also this Howto.

Include all jars in the classpath definition


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0587.html

Specifying all the required jar in the classpath can be a pain. Here some techniques to set the classpath
definition automatically.

Include all jars in the classpath definition 229


Real's HowTo PDF version

Windows batch file

For Windows 2000 (or better), we need a set of 3 CMD files to scan a given directory and build the
classpath defintion with all the jars found.

main.cmd

@echo off
call buildclasspath.cmd .\lib
Echo The Classpath definition is %CLASSPATH%
...
java MyClass

buildclasspath.cmd

set _CLASSPATH=%CLASSPATH%

set CLASSPATH=%1
for %%i in ( %1\*.jar ) do call buildclasspath_append.cmd %%~fsi

if "%_CLASSPATH%" == "" goto END


set CLASSPATH=%_CLASSPATH%;%CLASSPATH%

:END

buildclasspath_append.cmd

set CLASSPATH=%CLASSPATH%;%1

With XP (or better), it's simpler ... a single batch file can do the job.

@echo off
setlocal ENABLEDELAYEDEXPANSION
if defined CLASSPATH (set CLASSPATH=%CLASSPATH%;.) else (set CLASSPATH=.)
FOR /R .\lib %%G IN (*.jar) DO set CLASSPATH=!CLASSPATH!;%%G
Echo The Classpath definition is %CLASSPATH%
...
java MyClass

JDK6

According to http://java.sun.com/javase/6/docs/technotes/tools/windows/java.html, there is a new way to


include jars in a given directory without explicitly to specify each one of them.

As a special convenience, a class path element containing a


basename of * is considered equivalent to specifying a list
of all the files in the directory with the extension .jar
or .JAR (a java program cannot tell the difference between
the two invocations).

Include all jars in the classpath definition 230


Real's HowTo PDF version

For example, if directory foo contains a.jar and b.JAR, then


the class path element foo/* is expanded to a A.jar:b.JAR,
except that the order of jar files is unspecified. All jar files
in the specified directory, even hidden ones, are included in
the list. A classpath entry consisting simply of * expands to a
list of all the jar files in the current directory. The CLASSPATH
environment variable, where defined, will be similarly expanded.

Note : There is a bug when using this feature with JAVAW, see
http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6510337

Note : Use quote to avoid problem during the wildcard expansion, ex. javac -cp "C:\mylib\*"
HelloWorld.java

JAR (and ANT)

The best solution when you have a jar is to try to include the required jars into the manifest declaration.

Manifest-Version: 1.0
Class-Path:
customer_client.jar
mailer_client.jar
signon_client.jar

The manifest file format restrictions mandated by the JDK requires the use of a space ' ' character as the line
continuation character, so ensure that your editor is not set up to trim trailing spaces on saves and exits.

The line with the Class-Path: header must end with a space character and each of the lines referencing the
client jar's should start and end with a space ' ' character and the manifest file as a whole must end with a
blank line.

Remember that when you launch an application with


java -jar myjar.jar

the CLASSPATH definition (as defined by the environment variable) is overriden by the "class-path"
defined the jar's manifest.

See http://java.sun.com/docs/books/tutorial/deployment/jar/downman.html

Ant can be used to build your Jar and built the manifest class-path definition.

<target name="MyJar" depends="dist, compile" description="generate jar" >


<jar destfile="${dist}/${jar}">
<manifest>
<attribute name="Main-Class" value="${Main_Class}"/>
<attribute name="Class-Path" value=". lib/utils.jar lib/client.jar" />
</manifest>
</jar>

Include all jars in the classpath definition 231


Real's HowTo PDF version

</target>

It's possible (but not so simple) to do it automatically without specifying each jar one by one :

<path id="build.classpath">
<fileset dir="${basedir}"/>
<include name="lib/*.jar"/>
</fileset>
</path>

<pathconvert property="manifest.classpath" pathsep=" ">


<path refid="build.classpath"/>
<mapper>
<chainedmapper>
<flattenmapper/>
<globmapper from="*.jar" to="lib/*.jar"/>
</chainedmapper>
</mapper>
</pathconvert>

<target depends="compile" name="buildjar">


<jar jarfile="${basedir}/${test.jar}">
<fileset dir="${build}" />
<manifest>
<attribute name="Main-Class" value="com.mycompany.TestMain"/>
<attribute name="Class-Path" value="${manifest.classpath}"/>
</manifest>
</jar>
</target>

Latest Ant version (1.7) includes a task called ManifestClassPath which converts a classpath into a
space-separated list of items used to set the Manifest Class-Path attribute. See
http://ant.apache.org/manual/CoreTasks/manifestclasspath.html

<path id="build-classpath">
<fileset dir="${build.dir}">
<include name="*.jar"/>
</fileset>
</path>

<manifestclasspath property="lib.list" jarfile="${build.dir}/${jar.file}">


<classpath refid="build-classpath" />
</manifestclasspath>

<jar>
...
<manifest>
<attribute name="Main-Class" value="com.mycompany.TestMain"/>
<attribute name="Class-Path" value=". ${lib.list}"/>
</manifest>
...
</jar>

Include all jars in the classpath definition 232


Real's HowTo PDF version

Detect browser type from an Applet


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-detect-browser-type-from-an-applet.html

Call a Javascript from the Applet

With LiveConnect, we call a javascript to return the "User-Agent".

To compile, make sure that you have the plugin.jar in the classpath (or Eclipse Build Path). This jar is
usually located in [JRE]/lib folder. During runtime, it's already included by the Java plugin so you don't
have to worry about that.

The Java class

import java.applet.*;
import java.awt.event.*;
import java.awt.*;
import netscape.javascript.*;

public class GetUserAgent extends Applet


implements ActionListener {

private static final long serialVersionUID = 1L;

TextField tf;
Button b1;
JSObject win;

public void init(){


setLayout(new FlowLayout());
tf = new TextField(35);
b1 = new Button("get useragent from javascript");

b1.addActionListener(this);
add(tf);add(b1);
}

public void actionPerformed(ActionEvent ae) {


if (ae.getSource() == b1) {
JSObject win = (JSObject)JSObject.getWindow(this);
tf.setText((String)win.eval("getUserAgent();"));
}
}
}

Don't forget the MAYSCRIPT parameter in the APPLET tag, it's required since the Applet is using the
JSObject to interact with the Javascript.

Detect browser type from an Applet 233


Real's HowTo PDF version

<html>
<head>
<script>
function getUserAgent() {
return navigator.userAgent;
}
</script>
</head><body>
<applet code="GetUserAgent.class" MAYSCRIPT height=100 width=500></Applet>
</body>
</html>

Try it here

You need to parse the returned value to detect browser type. Look at this utility,
http://code.google.com/p/user-agent-utils/ or at this code : http://nerds.palmdrive.net/useragent/code.html
to get the idea.

Get the value from the server-side

When serving the HTML containing the Applet, you add the User-Agent as parameter for the Applet.

In a JSP/EL

<applet ... >


<param ... >
<param name="userAgent" value="${header['user-agent']}" />
</applet>

and in the Applet

String userAgent = getParameter("userAgent");

and parse the returned value...

Detect if Java is enabled from HTML


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0161.html

For a Javascript solution, check this How-to

<HTML><HEAD></HEAD><BODY>
<APPLET CODE="MyApplet.class"
NAME="myApplet"
HEIGHT=400 WIDTH=400 ALT="Oups! You don't have JAVA enabled">
<A HREF="nojava.html">Oups! You don't have JAVA enabled, click here.</A>
</APPLET>

Detect browser type from an Applet 234


Real's HowTo PDF version

</BODY></HTML>

See the Java Console Window Log (Java plugin)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0533.html

The Java Console Window Log is also stored on disk. On the Windows plateform, it's in the folder :

C:\Documents and Settings\


<username>\
Application Data\
Sun\
Java\
Deployment\
log

It's a file with the extension .trace

Written and compiled Réal Gagnon ©2015 [email protected]


http://www.rgagnon.com

Detect if Java is enabled from HTML 235


Internationalization
java-inter

Load resources based upon client environment at startup


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0133.html

There are two ways to include resources based on the current Locale. One way is to use Properties files and
the other are classes extending the ListResourceBundle base class. You need to follow a naming standard so
that the JVM retrieves the right resources bundle.

Note that if a resource is missing for the current locale then the default definition is used.

[International.java (main program)]

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import java.text.*;

public class International extends JFrame


implements ActionListener
{
JLabel aLabel;
JLabel vLabel;
JCheckBox aCheckbox;
JButton aButton;
JButton vButton;
JTextField aTextField;
NumberFormat nf;

public void initGUI(){


setLayout(new FlowLayout());

// String
aLabel = new JLabel
(MyResources.rb.getString("aLabel"));
add(aLabel);

// Object
aCheckbox =
(JCheckBox)MyResources.rb.getObject("aCheckbox");
add(aCheckbox);

// String concatenation with MessageFormat

Internationalization 236
Real's HowTo PDF version

Date d = new Date();


MessageFormat mf = new MessageFormat
(MyResources.rb.getString("aButton"));
aButton = new JButton
(mf.format(new Object [] { d }));
add(aButton);

// Number format output


double dn = 3.1416;
nf = (NumberFormat)
(MyResources.rb.getObject("aNumber"));
aTextField = new JTextField(6);
add(aTextField);
aTextField.setText(nf.format(dn));

// Number input validation


vButton =
(JButton)MyResources.rb.getObject("vButton");
add(vButton);
vButton.addActionListener(this);

vLabel = new JLabel("validation message ...");


add(vLabel);

setSize(400,400);
}

public void actionPerformed(ActionEvent ae) {


if (ae.getSource() == vButton) {
try {
nf.parse(aTextField.getText());
vLabel.setText(MyResources.rb.getString("numOK"));
vLabel.invalidate();
this.validate();
}
catch (ParseException pe) {
pe.printStackTrace();
vLabel.setText(MyResources.rb.getString("numERR"));
vLabel.invalidate();
this.validate();
}
}
}

public static void main(String args[]) {


System.out.println("Current Local : " + Locale.getDefault());
Thread t = new Thread () {
public void run() {
International frame = new International();
frame.initGUI();
frame.setVisible(true);
}
};

Load resources based upon client environment at startup 237


Real's HowTo PDF version

SwingUtilities.invokeLater(t);
}
}

[MyResources.java (default resources)]

import java.util.*;
import javax.swing.*;
import java.text.*;

public class MyResources extends ListResourceBundle {


public static ResourceBundle rb =
ResourceBundle.getBundle("MyResources");

public Object [][] getContents() {


return contents;
}

static final Object[][] contents = {


{ "myLabel" , "A Label" } ,
{ "aCheckbox", new JCheckBox("Yes") } ,
{ "aButton" , "Today {0,date,long}"},
{ "aNumber" , new DecimalFormat("0.####")},
{ "vButton" , new JButton("Validate number")},
{ "numOK" , "Valid!" },
{ "numERR" , "Invalid"}
};
}

[MyResources_en.java (english language resources)]


The classname format is [name][language ID][country code].java.
You can retrieve a list of language IDs and country codes at the Unicode organization Web site

import java.util.*;

public class MyResources_en extends ListResourceBundle {


public Object [][] getContents() {
return contents;
}
static final Object[][] contents = {
{ "aLabel" , "a Label (en)" }
};
}

[MyResources_fr.java (french language resources)]

import java.util.*;
import javax.swing.*;

public class MyResources_fr extends ListResourceBundle {


public Object [][] getContents() {
return contents;

Load resources based upon client environment at startup 238


Real's HowTo PDF version

static final Object[][] contents = {


{ "aLabel" , "une étiquette (fr)" } ,
{ "aCheckbox", new JCheckBox("Oui (fr)")} ,
{ "vButton" , new JButton("Validation du nombre")},
{ "numOK" , "Valide!"},
{ "numERR", "Invalide"}
};
}

[MyResources_fr_CA.java (french language (for Canada) resources)]

import java.util.*;

public class myResources_fr_CA extends ListResourceBundle {


public Object [][] getContents() {
return contents;
}

static final Object[][] contents = {


{ "aLabel" , "une étiquette (fr CA)" } ,
};
}

This example uses ListResourceBundle classes to store the required resources. It is possible to substitute them
for Properties files without any change to the code. The properties files must have the .properties extension.

See this How-to.

Load resources dynamically


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0134.html

This HowTo lets you select a language and change its GUI to reflect the choice.

We are using a special class, a ListResourceBundle, to store our resources. We have a class per Locale. If a
specific resource is not in a specific Locale ListResourceBundle then the default resource is used.

To use a properties file instead of a class to store resources then look at this HowTo.

[InternationalDynamic.java (main program)]

import java.util.*;
import java.text.*;
import java.awt.*;
import java.awt.event.*;

Load resources dynamically 239


Real's HowTo PDF version

import javax.swing.*;

public class InternationalDynamic extends JFrame


implements ActionListener
{

static Locale[] localesSupported = {


Locale.US, Locale.FRANCE, Locale.GERMANY
};

int localeChoosen = 0;
Locale localeCurrent;
ResourceBundle rb;

ButtonGroup bg;
JButton btnQuit;
JRadioButton r0, r1, r2;
JLabel today;
boolean defaultDone = false;

public void initLocale(){


localeCurrent = localesSupported[localeChoosen];
this.setLocale(localeCurrent);
rb = ResourceBundle.getBundle("ResourcesDynamic", localeCurrent);
}

public void initText() {


setTitle (rb.getString("title"));
r0.setText(rb.getString("r0"));
r1.setText(rb.getString("r1"));
r2.setText(rb.getString("r2"));
btnQuit.setText(rb.getString("btnQuit"));
Date d = new Date();
MessageFormat mf = new MessageFormat
(rb.getString("today"), localeCurrent);
today.setText(mf.format(new Object [] { d }));
}

public void initGUI(){


setLayout(new FlowLayout());

// RADIO buttons
bg = new ButtonGroup();
r0 = new JRadioButton();
r1 = new JRadioButton();
r2 = new JRadioButton();
bg.add(r0);
bg.add(r1);
bg.add(r2);
add(r0);
add(r1);
add(r2);

// default RADIO button

Load resources dynamically 240


Real's HowTo PDF version

if (!defaultDone) {
String rDef = rb.getString("rDefault");
if (rDef.equals("r0"))
r0.setSelected(true);
else if (rDef.equals("r1"))
r1.setSelected(true);
else
r2.setSelected(true);
defaultDone = true;
}
else {
if (localeChoosen == 0)
r0.setSelected(true);
else if (localeChoosen == 1)
r1.setSelected(true);
else
r2.setSelected(true);
}

// QUIT button
btnQuit = new JButton();
add(btnQuit);

// today label
today = new JLabel();
add(today);

//
r0.addActionListener(this);
r1.addActionListener(this);
r2.addActionListener(this);
btnQuit.addActionListener(this);

setSize(400,100);
setVisible(true);
}

public void actionPerformed(ActionEvent ae){


if (ae.getSource() == btnQuit) {
System.exit(0);
}
else if (ae.getSource() == r0) localeChoosen = 0;
else if (ae.getSource() == r1) localeChoosen = 1;
else if (ae.getSource() == r2) localeChoosen = 2;
initLocale();
initText();
pack();
}

public static void main(String args[]) {


System.out.println("Current Locale : " + Locale.getDefault());
Thread t = new Thread () {
public void run() {
InternationalDynamic i = new InternationalDynamic();

Load resources dynamically 241


Real's HowTo PDF version

i.initLocale();
i.initGUI();
i.initText();
i.pack();
}
};
SwingUtilities.invokeLater(t);
}
}

[ResourcesDynamic.java (default resources)]

import java.util.*;

public class ResourcesDynamic extends ListResourceBundle {


public Object [][] getContents() {
return contents;
}

static final Object[][] contents = {


{ "title", "Example" },
{ "r0" , "United States" } ,
{ "r1", "France" } ,
{ "r2" , "Germany"},
{ "rDefault" , "r0" },
{ "btnQuit" , "Quit"},
{ "today" , " (def) {0,date,long}"},
};
}

[ResourcesDynamic_en.java (english language resources)]

import java.util.*;

public class ResourcesDynamic_en extends ListResourceBundle {


public Object [][] getContents() {
return contents;
}

static final Object[][] contents = {


{ "title", "Example" },
{ "r0" , "United States" } ,
{ "r1", "France" } ,
{ "r2" , "Germany"},
{ "rDefault" , "r0" },
{ "btnQuit" , "Quit"},
{ "today" , " (en) {0,date,long}"},
};
}

[ResourcesDynamic_fr.java (french language resources)]

import java.util.*;

Load resources dynamically 242


Real's HowTo PDF version

public class ResourcesDynamic_fr extends ListResourceBundle {


public Object [][] getContents() {
return contents;
}

static final Object[][] contents = {


{ "title", "Exemple" },
{ "r0" , "Etats-Unis" } ,
{ "r1", "France" } ,
{ "r2", "Allemagne" },
{ "rDefault", "r1" },
{ "btnQuit", "Quitter" },
{ "today" , " (fr) {0,date, dd/MM/yyyy}"},
};
}

[ResourcesDynamic_de.java (german language resources)]

import java.util.*;

public class ResourcesDynamic_de extends ListResourceBundle {


public Object [][] getContents() {
return contents;
}
static final Object[][] contents = {
{ "title", "Beispiel" },
{ "r0" , "Vereinigte Staaten" } ,
{ "r1", "Frankreich" } ,
{ "r2", "Deutschland" },
{ "rDefault", "r2" },
{ "btnQuit", "verlassen"},
{ "today" , " (de) {0,date,dd.MM.yyyy}"},
};
}

Load resources via a resource file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0135.html

With the previous JAVA How-to, the resources were stored in classes. The drawback is when there is a
modification, we must recompile the class. With a resources file, we simply add or modify the resource in a
special file with a regular text editor. The JDK provides a class, PropertyResourceBundle, to use properties
file very easily. In fact, from the programmer's point of view, there is no difference if the resources are stored
in classes or properties files.

The ResourceBundle will look first for classes and if not found, it will look for properties files. We don't have
to specify filenames, the ResourceBundle will construct the filename using the same mechanism used for

Load resources via a resource file 243


Real's HowTo PDF version

classes. The file must have the extension .properties.

The ResourceBundle try to load the properties file from the current classpath.

If the properties are stored in subdirectory , use "." instead of "/".

For example, let's say that the properties file is in a subdirectory called "subdir" (from the current directory).
Then you can load the ResourcesDynamic resources file with

ResourceBundle.getBundle("subdir.ResourcesDynamic", localeCurrent);

[InternationalDynamic.java]

import java.util.*;
import java.text.*;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class InternationalDynamic extends JFrame


implements ActionListener
{

static Locale[] localesSupported = {


Locale.US, Locale.FRANCE, Locale.GERMANY
};

int localeChoosen = 0;
Locale localeCurrent;
ResourceBundle rb;

ButtonGroup bg;
JButton btnQuit;
JRadioButton r0, r1, r2;
JLabel today;
boolean defaultDone = false;

public void initLocale(){


localeCurrent = localesSupported[localeChoosen];
this.setLocale(localeCurrent);
rb = ResourceBundle.getBundle("res.ResourcesDynamic", localeCurrent);
}

public void initText() {


setTitle (rb.getString("title"));
r0.setText(rb.getString("r0"));
r1.setText(rb.getString("r1"));
r2.setText(rb.getString("r2"));
btnQuit.setText(rb.getString("btnQuit"));
Date d = new Date();
MessageFormat mf = new MessageFormat

Load resources via a resource file 244


Real's HowTo PDF version

(rb.getString("today"), localeCurrent);
today.setText(mf.format(new Object [] { d }));
}

public void initGUI(){


setLayout(new FlowLayout());

// RADIO buttons
bg = new ButtonGroup();
r0 = new JRadioButton();
r1 = new JRadioButton();
r2 = new JRadioButton();
bg.add(r0);
bg.add(r1);
bg.add(r2);
add(r0);
add(r1);
add(r2);

// default RADIO button


if (!defaultDone) {
String rDef = rb.getString("rDefault");
if (rDef.equals("r0"))
r0.setSelected(true);
else if (rDef.equals("r1"))
r1.setSelected(true);
else
r2.setSelected(true);
defaultDone = true;
}
else {
if (localeChoosen == 0)
r0.setSelected(true);
else if (localeChoosen == 1)
r1.setSelected(true);
else
r2.setSelected(true);
}

// QUIT button
btnQuit = new JButton();
add(btnQuit);

// today label
today = new JLabel();
add(today);

//
r0.addActionListener(this);
r1.addActionListener(this);
r2.addActionListener(this);
btnQuit.addActionListener(this);

Load resources via a resource file 245


Real's HowTo PDF version

setSize(400,100);
setVisible(true);
}

public void actionPerformed(ActionEvent ae){


if (ae.getSource() == btnQuit) {
System.exit(0);
}
else if (ae.getSource() == r0) localeChoosen = 0;
else if (ae.getSource() == r1) localeChoosen = 1;
else if (ae.getSource() == r2) localeChoosen = 2;
initLocale();
initText();
pack();
}

public static void main(String args[]) {


System.out.println("Current Locale : " + Locale.getDefault());
Thread t = new Thread () {
public void run() {
InternationalDynamic i = new InternationalDynamic();
i.initLocale();
i.initGUI();
i.initText();
i.pack();
}
};
SwingUtilities.invokeLater(t);
}
}

[RresourcesDynamic.properties]

title=Example
r0=United States
r1=France
r2=Germany
rDefault=r0
btnQuit=Quit
today=(def) {0,date,long}

[RresourcesDynamic_en.properties]

title=Example
r0=United States
r1=France
r2=Germany
rDefault=r0
btnQuit=Quit
today=(en) {0,date,long}

[ResourcesDynamic_fr.properties]

Load resources via a resource file 246


Real's HowTo PDF version

title=Exemple
r0=Etats-Unis
r1=France
r2=Allemagne
rDefault=r1
btnQuit=Quitte
today=(fr) {0,date, dd/MM/yyyy}

[ResourcesDynamic_de.properties]

title=Beispiel
r0=Vereinigte Staaten
r1=Frankreich
r2=Deutschland
rDefault=r2
btnQuit=Verlassen
today=(de) {0,date,dd.MM.yyyy}

Display "special character" using Unicode


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0136.html

The copyright symbol © :

String COPYRIGHT = "\u00a9";

The registered symbol ® :

String REGISTERED = "\u00ae";

The euro-currency sign € :

String EURO = "\u20ac"

For example :

import java.awt.*;
public class TestUnicode extends java.applet.Applet {

public static final String COPYRIGHT = "\u00a9";


public static final String REGISTERED = "\u00ae";
public static final String EURO = "\u20ac";

public void init () {


setLayout(new FlowLayout());
Label a = new Label(COPYRIGHT + " R\u00e9al Gagnon");
Label b = new Label(REGISTERED + " R\u00e9al's Software "
+ " price : 100 " + EURO);

Display "special character" using Unicode 247


Real's HowTo PDF version

add(a);
add(b);
}
}

Output :
Java not enabled!

A list of Unicode characters is available at the Unicode organization Web site.

Here a quick list for accented letters :

á \u00e0 Á \u00c0
à \u00e1 À \u00c1
â \u00e2 Â \u00c2
é \u00e9 É \u00c9
è \u00e8 È \u00c8
ê \u00ea Ê \u00ca
î \u00ee Î \u00ce
ç \u00e7 Ç \u00c7
The Indian rupee symbol ( ₹ HTML entity : &#x20B9;) is quite new (2010) so you need to make sure that
the Font that you are using has it. To display it from Java, you need to use Swing because AWT won't be able
to display it.
import java.awt.*;
import javax.swing.*;

public class TestUnicode extends JApplet {


public static final String RUPEE = "\u20B9";

public void init () {


setLayout(new FlowLayout());

JLabel b = new JLabel("rupee : " + RUPEE);


b.setFont(new Font("Arial", Font.PLAIN, 14));
add(b);
}
}

Display chinese/japanese characters in an Applet


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0137.html

A useful link to integrate international characters set in Netscape is


http://developer.netscape.com/software/jdk/i18n.html and check also

Display chinese/japanese characters in an Applet 248


Real's HowTo PDF version

http://www.geocities.com/Tokyo/Pagoda/1675/ for a more complete overview.

Localize a JOptionPane dialog


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0138.html

This example will show 2 radio buttons, one for english messages and buttons and the other one for french.
Press the button to display a localized JOptionPane according to the radio button selected.

Create 2 properties files, one for english , one for french.

[JOptionPane_en.properties]
Yes=Yes
No=No
Cancel=Cancel
SaveMsg=Do you want to save your data

[JOptionPane_fr.properties]
Yes=Oui
No=Non
Cancel=Annuler
SaveMsg=Voulez-vous sauvegarder vos donnees

Then

import javax.swing.*;
import java.awt.event.*;
import java.awt.*;
import java.util.*;

public class MessageBoxExample extends JPanel


implements ActionListener {
JButton go;
AbstractButton button;
ButtonGroup group;
Locale locale;
String msg ;

public MessageBoxExample() {
group = new ButtonGroup();

locale = Locale.US; // default value


button = new JRadioButton("English", true);
button.setActionCommand("en");
button.addActionListener(this);
group.add(button);
add(button);

Localize a JOptionPane dialog 249


Real's HowTo PDF version

button = new JRadioButton("Francais");


button.setActionCommand("fr");
button.addActionListener(this);
group.add(button);
add(button);

go = new JButton("Do it");


go.addActionListener(this);
add(go);

locale = Locale.US;
}

public void setUILanguage() {


ResourceBundle rb;
rb = ResourceBundle.getBundle("JOptionPane", locale);

UIManager.put("OptionPane.yesButtonText", rb.getString("Yes"));
UIManager.put("OptionPane.noButtonText", rb.getString("No"));
UIManager.put("OptionPane.cancelButtonText", rb.getString("Cancel"));
msg = rb.getString("SaveMsg");
}

public void actionPerformed(ActionEvent e) {


int result;

if (e.getSource() instanceof JRadioButton) {


if (e.getActionCommand().equals("en"))
locale = Locale.US;
else
locale = Locale.FRANCE;
setUILanguage();
}
else {
// the button action
result = JOptionPane.showConfirmDialog(this,msg);
System.out.println(result);
}
}

public Dimension getPreferredSize(){


return new Dimension(200, 200);
}

public static void main(String s[]) {


JFrame frame = new JFrame("");
MessageBoxExample panel = new MessageBoxExample();
frame.addWindowListener(
new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);

Localize a JOptionPane dialog 250


Real's HowTo PDF version

frame.getContentPane().add(panel,"Center");
frame.setSize(panel.getPreferredSize());
frame.setVisible(true);
}
}

Validate/Convert a number using the current Locale()


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0139.html

Depending on the International setting, numbers with comma as decimal separator may be permitted. The
NumberFormat class can handle this based on the current Locale().

import java.text.NumberFormat;
import java.text.ParseException;
import java.util.Locale;

public class NumberUtils {

private NumberUtils() {}

public static double getDoubleValue(String value) throws ParseException {


// use the default locale
return NumberUtils.getDoubleValue(Locale.getDefault(), value);
}

public static double getDoubleValue(Locale loc, String value)


throws ParseException {
// use the default locale
return NumberFormat.getInstance(loc).parse(value).doubleValue();
}

public static String convertStringAsStringNumberUnLocalized(String value)


throws ParseException {
// use the default locale
return convertStringAsStringNumberUnLocalized(Locale.getDefault(), value);
}

public static String convertStringAsStringNumberUnLocalized


(Locale loc, String value) throws ParseException {
double d = NumberUtils.getDoubleValue(loc, value);
return NumberFormat.getInstance(new Locale("us")).format(d);
}

public static void main(String[] args) throws Exception{


System.out.println(Locale.getDefault());
System.out.println(NumberUtils.getDoubleValue("42,24"));
System.out.println(NumberUtils.getDoubleValue("42.24"));
System.out.println(NumberUtils.convertStringAsStringNumberUnLocalized

Validate/Convert a number using the current Locale() 251


Real's HowTo PDF version

(new Locale("fr"), "42,24"));


/*
* output
* fr_CA
* 42.24
* 42.0
* 42.24
*/
}
}

Localize a JFileChooser
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0299.html

Modern Swing release have now built-in ready-to-use translations for the JFileChooser. The language is
choosen based on the current Locale. So you don't have to do anything to display the JFileChooser in the right
language.

The user interface elements provided by the J2SE Runtime Environment 5.0, include Swing dialogs, messages
written by the runtime environment to the standard output and standard error streams, as well as messages
produced by the tools provided with the JRE. These user interface elements are localized into the following
languages:

Language Locale ID
Chinese (Simplified) zh_CN
Chinese (Traditional) zh_TW
English en
French fr
German de
Italian it
Japanese ja
Korean ko
Spanish es
Swedish sv
Sun Supported Locales

This example will show 2 radio buttons, one for english, one for french. Press the button to display a localized
JFileChooser according to the radio button selected.

Localize a JFileChooser 252


Real's HowTo PDF version

Create 2 properties files, one for english , one for french (these files are incomplete but should be enough to
get you started).

[JFileChooser_en.properties]

Title=Real's JFileChooser
lookInLabelText=Current
filesOfTypeLabelText=File type
upFolderToolTipText=go up

[JFileChooser_fr.properties]

Title=JFileChooser de R\u00e9al
lookInLabelText=Courant
filesOfTypeLabelText=Type de fichier
upFolderToolTipText=Remonte

Then

[LocalizeJFileChooser.java]

import javax.swing.*;
import java.awt.event.*;
import java.awt.*;
import java.util.*;

public class LocalizeJFileChooser extends JPanel


implements ActionListener {
JButton go;
AbstractButton button;
ButtonGroup group;
Locale locale;
String msg ;

protected JFileChooser z_chooser;


String z_choosertitle;

public LocalizeJFileChooser() {
group = new ButtonGroup();

locale = Locale.US; // default value


button = new JRadioButton("English", true);
button.setActionCommand("en");
button.addActionListener(this);
group.add(button);
add(button);

button = new JRadioButton("Francais");


button.setActionCommand("fr");
button.addActionListener(this);
group.add(button);

Localize a JFileChooser 253


Real's HowTo PDF version

add(button);

go = new JButton("Do it");


go.addActionListener(this);
add(go);

locale = Locale.US;

public void setUILanguage() {


ResourceBundle rb;
rb = ResourceBundle.getBundle("JFileChooser", locale);

z_choosertitle = rb.getString("Title");

UIManager.put
("FileChooser.lookInLabelText",
rb.getString("lookInLabelText"));
UIManager.put
("FileChooser.filesOfTypeLabelText",
rb.getString("filesOfTypeLabelText"));
UIManager.put
("FileChooser.upFolderToolTipText",
rb.getString("upFolderToolTipText"));
/*
do the same with :
FileChooser.fileNameLabelText
FileChooser.homeFolderToolTipText
FileChooser.newFolderToolTipText
FileChooser.listViewButtonToolTipTextlist
FileChooser.detailsViewButtonToolTipText
FileChooser.saveButtonText=Save
FileChooser.openButtonText=Open
FileChooser.cancelButtonText=Cancel
FileChooser.updateButtonText=Update
FileChooser.helpButtonText=Help
FileChooser.saveButtonToolTipText=Save
FileChooser.openButtonToolTipText=Open
FileChooser.cancelButtonToolTipText=Cancel
FileChooser.updateButtonToolTipText=Update
FileChooser.helpButtonToolTipText=Help

Almost all Swing widgets can be customize this way. You can
examine the Swing sources to get these values or check
http://www.gargoylesoftware.com/papers/plafdiff.html for
a list of them.

*/

public void actionPerformed(ActionEvent e) {


int result;

Localize a JFileChooser 254


Real's HowTo PDF version

if (e.getSource() instanceof JRadioButton) {


if (e.getActionCommand().equals("en"))
locale = Locale.US;
else
locale = Locale.FRANCE;
setUILanguage();
}
else {
z_chooser = new JFileChooser();
z_chooser.setCurrentDirectory(new java.io.File("."));
z_chooser.setDialogTitle(z_choosertitle);
if (z_chooser.showOpenDialog(this) !=
JFileChooser.APPROVE_OPTION)
return;
}
}

public Dimension getPreferredSize(){


return new Dimension(200, 200);
}

public static void main(String s[]) {


JFrame frame = new JFrame("");
LocalizeJFileChooser panel = new LocalizeJFileChooser();
frame.addWindowListener(
new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
frame.getContentPane().add(panel,"Center");
frame.setSize(panel.getPreferredSize());
frame.setVisible(true);
}
}

Disable localization
Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0418.html

By default, the JVM uses the current locale as defined by the OS. To bypass this configuration, you specify on
the command line the locale to be used :

java -Duser.language=en -Duser.region=US MyApplication

Disable localization 255


Real's HowTo PDF version

Generate the Javadoc "en français"


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0437.html

The javadoc utility uses the regular Java mechanism to internationalize its output. The tools.jar in the lib
directory contains the resource bundle standard.properties used by Javadoc to generated the labels. To add a
new language, you need to create the appropriate resource bundle, in our case for french, we need a file called
standard_fr.properties.

The new file must be in the package com.sun.tools.doclets.standard.resources.

Extract from tools.jar, the standard.properties files (keep the directory structure). Copy it under the name
standard_fr.properties. Translate it (or you can download my "incomplete" version here).

[standard.properties (extract)]

doclet.Window_Split_Index={0}\: {1}-Index
doclet.Packages=Packages
doclet.SerialData=Serial Data\:
doclet.Since=Since\:
doclet.Warn_inline_taglet=Inline tag {0} should only be used with a {1}.
doclet.ClassUse_Subinterface=Subinterfaces of {0} in {1}
doclet.Frame_Version=Frame version
doclet.Generated_Docs_Untitled=Generated Documentation (Untitled)

[standard_fr.properties (extract)]

doclet.Window_Split_Index={0}\: {1}-Index
doclet.Packages=Paquetages
doclet.SerialData=Donn\u00E9e s\u00E9rialis\u00E9e\:
doclet.Since=Depuis\:
doclet.Warn_inline_taglet=Inline tag {0} should only be used with a {1}.
doclet.ClassUse_Subinterface=Sous-interfaces de {0} dans {1}
doclet.Frame_Version=Version avec cadres
doclet.Generated_Docs_Untitled=Documentation g\u00E9n\u00E9r\u00E9e

Once everything translated, put your standard_fr.properties into the tools.jar making sure that the file is
located in the right package (along standard.properties in com.sun.tools.doclets.standard.resources).

To generate in french, use the -locale switch on the command line

javadoc -locale fr ....

NOTE : Make sure the -locale switch is the first one.

Using Ant,

Generate the Javadoc "en français" 256


Real's HowTo PDF version

<javadoc
locale="fr"
sourcefiles="c:/client/Client.java"
destdir="javadoc/Client"
author="true"
version="true"
use="true"
private="true"
windowtitle="Client">
<doctitle><![CDATA[<h1>Client</h1>]]></doctitle>
<bottom><![CDATA[<i>Copyright &#169; 2003 Real's Howto.</i>]]></bottom>
</javadoc>

Sort an array with international characters


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0343.html

Sort utilities are now part of latest JDK versions.

Case sensitive

java.util.Arrays.sort(myArray);

Case insensitive

java.util.Arrays.sort(myArray, String.CASE_INSENSITIVE_ORDER);

Sort with international characters.

Take the following example :

import java.util.*;
import java.io.*;

public class TestSort1 {

static String [] words = { "Réal", "Real", "Raoul", "Rico" };

public static void main(String args[]) throws Exception {


try {
Writer w = getWriter();
w.write("Before :\n");

for (String s : words) {


w.write(s + " ");
}

java.util.Arrays.sort(words);

Sort an array with international characters 257


Real's HowTo PDF version

w.write("\nAfter :\n");
for (String s : words) {
w.write(s + " ");
}
w.flush();
w.close();
}
catch(Exception e){
e.printStackTrace();
}

// useful to output accentued characters to the console


public static Writer getWriter() throws UnsupportedEncodingException {
if (System.console() == null) {
Writer w =
new BufferedWriter
(new OutputStreamWriter(System.out, "Cp850"));
return w;
}
else {
return System.console().writer();
}
}
}

The output is :

Before :
Réal Real Raoul Rico
After :
Raoul Real Rico Réal

which is wrong since we expect to find "Réal" after "Real".

To solve the problem , replace

java.util.Arrays.sort(words);

by

java.util.Arrays.sort(words, java.text.Collator.getInstance(java.util.Locale.FRENCH));
// or
// java.util.Arrays.sort(words, java.text.Collator.getInstance());

and the output will be :

Before :
Réal Real Raoul Rico

Sort an array with international characters 258


Real's HowTo PDF version

After :
Raoul Real Réal Rico

Or you can do it the long way :

import java.util.Locale;
import java.text.Collator;

...
Locale loc = Locale.FRENCH;
sortArray(Collator.getInstance(loc), words);
...

public static void sortArray(Collator collator, String[] strArray) {


String tmp;
if (strArray.length == 1) return;
for (int i = 0; i < strArray.length; i++) {
for (int j = i + 1; j < strArray.length; j++) {
if( collator.compare(strArray[i], strArray[j] ) > 0 ) {
tmp = strArray[i];
strArray[i] = strArray[j];
strArray[j] = tmp;
}
}
}
}

See this HowTo

Accentuated characters in Properties/ResourceBundle file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0492.html

The rules are

• Only use ISO Latin 1 characters in the Properties/ResourceBundle files


• For other characters use the \u.... notation
• To avoid having to type all the \u... notation manually, use the native2ascii tool (included with the
SDK).

Compare accentuated letters


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0496.html

Accentuated characters in Properties/ResourceBundle file 259


Real's HowTo PDF version

From the javadoc,

the result of String.compareTo() is a negative integer


if this String object lexicographically precedes the
argument string. The result is a positive integer if
this String object lexicographically follows the argument
string. The result is zero if the strings are equal;
compareTo returns 0 exactly when the equals(Object)
method would return true.

In this code, we have 2 strings, "état" and "famille". We expect that "état" is before "famille". But
String.compareTo() will return that "famille" is before "état".

class Test {
public static void main(String args[]) {

String s1 = "état";
String s2 = "famille";

// here we are expecting "é" < "f"


if (s1.compareTo(s2) > 0) {
if (s1.compareTo(s2) > 0) {
// s1 lexicographically follows s2 which is not true!
System.out.println("not ok " + s1 + " > " + s2 );
}
}
/*
output :
not ok état > famille
*/
}

The fix is to use java.text.Collator.compareTo(). From the javadoc :

Collator.compare() compares the source string to the target string


according to the collation rules for this Collator.
Returns an integer less than, equal to or greater than zero
depending on whether the source String is less than,
equal to or greater than the target string.

import java.text.Collator;

public class Test {


public static void main(String args[]) {

String s1 = "état";
String s2 = "famille";

// Collator c = Collator.getInstance(java.util.Locale.FRANCE);
Collator c = Collator.getInstance();
c.setStrength(Collator.PRIMARY);

Compare accentuated letters 260


Real's HowTo PDF version

if (c.compare(s1, s2) < 0) {


// s2 lexicographically follows s1
System.out.println("ok " + s1 + " < " + s2);
}
}
/*
output :
ok état < famille
*/

Equality

To compare without taking into account the presence of accentued so that "é" == "e", we use a Collator.

import java.text.Collator;
// import java.util.Locale;

public class TextTest {

public static void main(String ... args) {


String a = "Real";
String b = "Réal";

System.out.println(a + " and " + b + " equals? " +


check(a,b));
/*
* output :
* Real and Réal equals? true
*/
}

public static boolean check(String a, String b) {


// Collator c = Collator.getInstance(Locale.US);
//
// accent and upper/lowercase not taken into account
Collator c = Collator.getInstance();
c.setStrength(Collator.PRIMARY);
return (c.compare(a,b) == 0 );
}
}

See this HowTo.

Remove accent from letters (ex .é to e)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0456.html

Remove accent from letters (ex .é to e) 261


Real's HowTo PDF version

The following snippets remove from a String accented letters and replace them by their regular ASCII
equivalent.

These can be useful before inserting data into a database to made sorting easier.

Using java.text.Normalizer

It's a simple using the java.text.Normalizer class.

We are calling the normalize(). If we pass à, the method returns a + ` . Then using a regular expression, we
clean up the string to keep only valid US-ASCII characters.

import java.text.Normalizer;
import java.util.regex.Pattern;

public class StringUtils {


private StringUtils() {}

public static String unAccent(String s) {


//
// JDK1.5
// use sun.text.Normalizer.normalize(s, Normalizer.DECOMP, 0);
//
String temp = Normalizer.normalize(s, Normalizer.Form.NFD);
Pattern pattern = Pattern.compile("\\p{InCombiningDiacriticalMarks}+");
return pattern.matcher(temp).replaceAll("");
}

public static void main(String args[]) throws Exception{


String value = "é à î _ @";
System.out.println(StringUtils.unAccent(value));
// output : e a i _ @
}
}

Using String.replaceAll()

As an alternative, replaceAll() and regular expressions on a String can also be used :

public class Test {


public static void main(String args[]) {
String s = "È,É,Ê,Ë,Û,Ù,Ï,Î,À,Â,Ô,è,é,ê,ë,û,ù,ï,î,à,â,ô";

s = s.replaceAll("[èéêë]","e");
s = s.replaceAll("[ûù]","u");
s = s.replaceAll("[ïî]","i");
s = s.replaceAll("[àâ]","a");
s = s.replaceAll("Ô","o");

s = s.replaceAll("[ÈÉÊË]","E");

Remove accent from letters (ex .é to e) 262


Real's HowTo PDF version

s = s.replaceAll("[ÛÙ]","U");
s = s.replaceAll("[ÏÎ]","I");
s = s.replaceAll("[ÀÂ]","A");
s = s.replaceAll("Ô","O");

System.out.println(s);
// output : E,E,E,E,U,U,I,I,A,A,O,e,e,e,e,u,u,i,i,a,a,o
}
}

The String.indexOf()

While the two techniques above are ok... there are a little bit slow.

The following HowTo is faster because we using one String to contain all the possible characters to be
converted and a String with the ASCII equivalent. So we need to detect the position in the first String and then
do a lookup in the second String.

public class AsciiUtils {


private static final String PLAIN_ASCII =
"AaEeIiOoUu" // grave
+ "AaEeIiOoUuYy" // acute
+ "AaEeIiOoUuYy" // circumflex
+ "AaOoNn" // tilde
+ "AaEeIiOoUuYy" // umlaut
+ "Aa" // ring
+ "Cc" // cedilla
+ "OoUu" // double acute
;

private static final String UNICODE =


"\u00C0\u00E0\u00C8\u00E8\u00CC\u00EC\u00D2\u00F2\u00D9\u00F9"
+ "\u00C1\u00E1\u00C9\u00E9\u00CD\u00ED\u00D3\u00F3\u00DA\u00FA\u00DD\u00FD"
+ "\u00C2\u00E2\u00CA\u00EA\u00CE\u00EE\u00D4\u00F4\u00DB\u00FB\u0176\u0177"
+ "\u00C3\u00E3\u00D5\u00F5\u00D1\u00F1"
+ "\u00C4\u00E4\u00CB\u00EB\u00CF\u00EF\u00D6\u00F6\u00DC\u00FC\u0178\u00FF"
+ "\u00C5\u00E5"
+ "\u00C7\u00E7"
+ "\u0150\u0151\u0170\u0171"
;

// private constructor, can't be instanciated!


private AsciiUtils() { }

// remove accentued from a string and replace with ascii equivalent


public static String convertNonAscii(String s) {
if (s == null) return null;
StringBuilder sb = new StringBuilder();
int n = s.length();
for (int i = 0; i < n; i++) {
char c = s.charAt(i);
int pos = UNICODE.indexOf(c);

Remove accent from letters (ex .é to e) 263


Real's HowTo PDF version

if (pos > -1){


sb.append(PLAIN_ASCII.charAt(pos));
}
else {
sb.append(c);
}
}
return sb.toString();
}

public static void main(String args[]) {


String s =
"The result : È,É,Ê,Ë,Û,Ù,Ï,Î,À,Â,Ô,è,é,ê,ë,û,ù,ï,î,à,â,ô,ç";
System.out.println(AsciiUtils.convertNonAscii(s));
// output :
// The result : E,E,E,E,U,U,I,I,A,A,O,e,e,e,e,u,u,i,i,a,a,o,c
}
}

Thanks to MV Bastos for the "tilde" bug fix


Thanks to L.. Tama for the missing Ñ !
Thanks to T. Hague for the missing "double acute";

As a bonus, here a method to convert a given string to uppercase with no accent. This can be useful in a
database field to simplify name searching with accent or not.

public class StringUtils {


private StringUtils() {}

private static final String UPPERCASE_ASCII =


"AEIOU" // grave
+ "AEIOUY" // acute
+ "AEIOUY" // circumflex
+ "AON" // tilde
+ "AEIOUY" // umlaut
+ "A" // ring
+ "C" // cedilla
+ "OU" // double acute
;

private static final String UPPERCASE_UNICODE =


"\u00C0\u00C8\u00CC\u00D2\u00D9"
+ "\u00C1\u00C9\u00CD\u00D3\u00DA\u00DD"
+ "\u00C2\u00CA\u00CE\u00D4\u00DB\u0176"
+ "\u00C3\u00D5\u00D1"
+ "\u00C4\u00CB\u00CF\u00D6\u00DC\u0178"
+ "\u00C5"
+ "\u00C7"
+ "\u0150\u0170"
;

public static String toUpperCaseSansAccent(String txt) {


if (txt == null) {

Remove accent from letters (ex .é to e) 264


Real's HowTo PDF version

return null;
}
String txtUpper = txt.toUpperCase();
StringBuilder sb = new StringBuilder();
int n = txtUpper.length();
for (int i = 0; i < n; i++) {
char c = txtUpper.charAt(i);
int pos = UPPERCASE_UNICODE.indexOf(c);
if (pos > -1){
sb.append(UPPERCASE_ASCII.charAt(pos));
}
else {
sb.append(c);
}
}
return sb.toString();
}

public static void main(String args[]) throws Exception {


String s =
"The result : È,É,Ê,Ë,Û,Ù,Ï,Î,À,Â,Ô,è,é,ê,ë,û,ù,ï,î,à,â,ô,ç";
System.out.println(
StringUtils.toUpperCaseSansAccent(s));
// output :
// THE RESULT : E,E,E,E,U,U,I,I,A,A,O,E,E,E,E,U,U,I,I,A,A,O,C
}
}

Output accentuated characters to the console


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0046.html

Java 1.6 or more

In Java 1.6 you can use System.console() instead of System.out.println() to display accentuated characters to
console.

public class Test2 {


public static void main(String args[]){
String s = "caractères français : à é \u00e9"; // Unicode for "é"
System.out.println(s);
System.console().writer().println(s);
}
}

anf the output is

Output accentuated characters to the console 265


Real's HowTo PDF version

C:\temp>java Test
caractþres franþais : Ó Ú Ú
caractères français : à é é

Java 1.5 or less

When starting the JVM and pass on the command line the default file encoding to be used. Then you will be
able to use regular System.out.println().

java -Dfile.encoding=Cp850 MyApp

Another way is to specify in the code the encoding to be used.

import java.io.*;

public class Test {


public static void main(String[] args) {
PrintStream ps = null;
String javaString =
"caractères français : à é \u00e9"; // Unicode for "é"

try {
ps = new PrintStream(System.out, true, "Cp850");
}
catch (UnsupportedEncodingException error) {
System.err.println(error);
System.exit(0);
}
ps.println(javaString);
}
}

Note : List of supported encodings here

Get the default character set of the JVM


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0505.html

public class Hello {


public static void main(String args[]) throws Exception{
// not crossplateform safe
System.out.println(System.getProperty("file.encoding"));
// jdk1.4
System.out.println(
new java.io.OutputStreamWriter(
new java.io.ByteArrayOutputStream()).getEncoding()
);
// jdk1.5

Output accentuated characters to the console 266


Real's HowTo PDF version

System.out.println(java.nio.charset.Charset.defaultCharset().name());
}
}

Output example (winXP)

>java Hello
Cp1252
Cp1252
windows-1252

See also java encoding table for the encoding sets supported.

Convert OEM (DOS) file to Ansi (Windows)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0524.html

We are using an InputStreamReader which convert the specified input encoding to Unicode and an
OutputStreamWriter which from Unicode to the specified output encoding.

This can be useful when migrating data from a legacy database (ex. Clipper, dBase) to newer DBMS (ex.
mySQL, Sybase).

import java.io.*;

public class OemToAnsi {

public static void main(String args[]) throws Exception{


if (args.length != 2) {
System.out.println(
"Usage : java OemToAnsi inputdosfile outputansifile"
);
System.out.println(
" note : codepage input Cp850 codepage output Cp1252"
);
System.exit(1);
}
// input
FileInputStream fis = new FileInputStream(args[0]);
BufferedReader r =
new BufferedReader(new InputStreamReader(fis, "Cp850"));
// output
FileOutputStream fos = new FileOutputStream(args[1]);
Writer w =
new BufferedWriter(new OutputStreamWriter(fos, "Cp1252"));
String oemString = "";
while ( (oemString= r.readLine()) != null) {
w.write(oemString);

Get the default character set of the JVM 267


Real's HowTo PDF version

w.flush();
}
w.close();
r.close();
System.exit(0);
}
}

See also this related HowTo

Detect non-ASCII character in a String


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0536.html

import java.nio.ByteBuffer;
import java.nio.CharBuffer;
import java.nio.charset.Charset;
import java.nio.charset.CharsetDecoder;
import java.nio.charset.CharacterCodingException;

public class StringUtils {


private StringUtils() {}

public static boolean isPureAscii(String v) {


byte bytearray [] = v.getBytes();
CharsetDecoder d = Charset.forName("US-ASCII").newDecoder();
try {
CharBuffer r = d.decode(ByteBuffer.wrap(bytearray));
r.toString();
}
catch(CharacterCodingException e) {
return false;
}
return true;
}

public static void main (String args[]) throws Exception {


String test = "Réal";
System.out.println(test + " isPureAscii() : " + StringUtils.isPureAscii(test));
test = "Real";
System.out.println(test + " isPureAscii() : " + StringUtils.isPureAscii(test));
/*
* output :
* Réal isPureAscii() : false
* Real isPureAscii() : true
*/
}
}

Convert OEM (DOS) file to Ansi (Windows) 268


Real's HowTo PDF version

A different (and simpler) approach is to take a given string and check if it's possible to encode it into ASCII.

import java.nio.charset.Charset;
import java.nio.charset.CharsetEncoder;

public class StringUtils {

static CharsetEncoder asciiEncoder =


Charset.forName("US-ASCII").newEncoder(); // or "ISO-8859-1" for ISO Latin 1

public static boolean isPureAscii(String v) {


return asciiEncoder.canEncode(v);
}

public static void main (String args[]) throws Exception {


String test = "Réal";
System.out.println(test + " isPureAscii() : " + StringUtils.isPureAscii(test));
test = "Real";
System.out.println(test + " isPureAscii() : " + StringUtils.isPureAscii(test));

/*
* output :
* Réal isPureAscii() : false
* Real isPureAscii() : true
*/
}
}

Another way is to use a regular expression, see this Javascript HowTo for a hint!

To simply strip any non-ascii characters form a string


public class Test {
public static void main(String args[]){
String input = "eéaà";
String output = input.replaceAll("[^\\p{ASCII}]", "");
System.out.println(output);
/*
* output : ea
*/
}
}

See also Unaccent letters.

Get the month (or day) name (localized)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0650.html

Detect non-ASCII character in a String 269


Real's HowTo PDF version

import java.text.DateFormatSymbols;
import java.util.Locale;

public class DateUtils {


private DateUtils() { }

public static String getMonthName(int month) {


return getMonthName(month, Locale.getDefault());
}

public static String getMonthName(int month, Locale locale) {


DateFormatSymbols symbols = new DateFormatSymbols(locale);
String[] monthNames = symbols.getMonths();
return monthNames[month - 1];
}

public static String getDayName(int day, Locale locale) {


DateFormatSymbols symbols = new DateFormatSymbols(locale);
String[] dayNames = symbols.getWeekdays();
return dayNames[day];
}

public static void main(String[] args) {

System.out.println(DateUtils.getMonthName(1));
System.out.println(DateUtils.getMonthName(1, new Locale("it")));

System.out.println
(DateUtils.getDayName(java.util.Calendar.SUNDAY, Locale.getDefault()));

/*
* output :
* january
* gennaio
* sunday
*/
}
}

Written and compiled Réal Gagnon ©2015 [email protected]


http://www.rgagnon.com

Get the month (or day) name (localized) 270


IO
java-io

Redirect output(stdout/stderr) to a frame


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0028.html

[JDK1.1]

import java.awt.*;
import java.awt.event.*;
import java.io.*;

public class RedirectedFrame extends Frame {


TextArea aTextArea = new TextArea();
PrintStream aPrintStream =
new PrintStream(
new FilteredStream(
new ByteArrayOutputStream()));

boolean logFile;

RedirectedFrame(boolean logFile) {
this.logFile = logFile;
System.setOut(aPrintStream);
System.setErr(aPrintStream);
setTitle("Error message");
setSize(500,300);
setLayout(new BorderLayout());
add("Center" , aTextArea);
displayLog();
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
dispose();
}
}
);
}

class FilteredStream extends FilterOutputStream {


public FilteredStream(OutputStream aStream) {
super(aStream);
}

public void write(byte b[]) throws IOException {


String aString = new String(b);

IO 271
Real's HowTo PDF version

aTextArea.append(aString);
}

public void write(byte b[], int off, int len) throws IOException {
String aString = new String(b , off , len);
aTextArea.append(aString);
if (logFile) {
FileWriter aWriter = new FileWriter("error.log", true);
aWriter.write(aString);
aWriter.close();
}
}
}

public void displayLog() {


Dimension dim = getToolkit().getScreenSize();
Rectangle abounds = getBounds();
Dimension dd = getSize();
setLocation((dim.width - abounds.width) / 2,
(dim.height - abounds.height) / 2);
setVisible(true);
requestFocus();
}

public static void main(String s[]){


try {
// force an exception for demonstration purpose
Class.forName("unknown").newInstance();
}
catch (Exception e) {
// for applet, always RedirectedFrame(false)
RedirectedFrame r = new RedirectedFrame(true);
e.printStackTrace();
}
}
}

Check also this simple Swing solution.

Redirect printStackTrace() to a String


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0029.html

import java.io.*;

public class TestStack2String {


public static void main(String s[]){
try {
// force an exception for demonstration purpose

Redirect output(stdout/stderr) to a frame 272


Real's HowTo PDF version

Class.forName("unknown").newInstance();
// or this could be changed to:
// throw new Exception();

}
catch (Exception e) {
System.out.println(stack2string(e));
}
}

public static String stack2string(Exception e) {


try {
StringWriter sw = new StringWriter();
PrintWriter pw = new PrintWriter(sw);
e.printStackTrace(pw);
return "------\r\n" + sw.toString() + "------\r\n";
}
catch(Exception e2) {
return "bad stack2string";
}
}
}

Redirect to NULL device


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0453.html

This can be useful if you want to suppress all output.

// Unix style
PrintStream nps = new PrintStream(new FileOutputStream("/dev/null"));
System.setErr(nps);
System.setOut(nps);

//Windows style
PrintStream nps = new PrintStream(new FileOutputStream("NUL:"));
System.setErr(nps);
System.setOut(nps);

//One-liner style : subclass OutputStream to override the write method ...


System.setOut(new java.io.PrintStream(
new java.io.OutputStream() {
public void write(int b){}
}
));

You may want to suppress output done with the regular System.out but maintain the ability to write to the
original streams directly when necessary.

Redirect printStackTrace() to a String 273


Real's HowTo PDF version

// Keep a copy of the original out stream.


PrintStream original = new PrintStream(System.out);

// replace the System.out, here I redirect to NUL (for demonstration)


System.setOut(new PrintStream(new FileOutputStream("NUL:")));
System.out.println("bar"); // no output

// The original stream is still available


original.println("foo"); // output to stdout

See also Get faster console output (System.out.println() replacement).

Print a text file using the javax.print API


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-print-a-text-file-with-javax.print-api.html

This example will print a given text file using the javax.print API.
• With cheap personal printer (at least with mine!), you cannot select many options... more than one copy and
page orientation (portrait or landscape) won't work.
• You need to set the "flavor" as AUTOSENSE so the content is sent as "OCTET-STREAM" even if it's
possible, according to the Javadoc, to set the "flavor" as UTF8 or US_ASCII. I believe this is a limitation of
the Windows platform implementation.
• You need to send a FORMFEED between each print job to eject the last page.
• A special class, PrintJobWatcher, is used to wait for the completion of a print job.
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.File;
import java.io.FileInputStream;

import javax.print.Doc;
import javax.print.DocFlavor;
import javax.print.DocPrintJob;
import javax.print.PrintException;
import javax.print.PrintService;
import javax.print.PrintServiceLookup;
import javax.print.SimpleDoc;

import javax.print.attribute.HashPrintRequestAttributeSet;
import javax.print.attribute.PrintRequestAttributeSet;
import javax.print.attribute.standard.Copies;

import javax.print.event.PrintJobAdapter;
import javax.print.event.PrintJobEvent;

public class PrintTextFile {

public static void main(String[] args) throws PrintException, IOException {

Redirect to NULL device 274


Real's HowTo PDF version

String defaultPrinter =
PrintServiceLookup.lookupDefaultPrintService().getName();
System.out.println("Default printer: " + defaultPrinter);

PrintService service = PrintServiceLookup.lookupDefaultPrintService();

FileInputStream in = new FileInputStream(new File("c:/temp/foo.txt"));

PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();


pras.add(new Copies(1));

DocFlavor flavor = DocFlavor.INPUT_STREAM.AUTOSENSE;


Doc doc = new SimpleDoc(in, flavor, null);

DocPrintJob job = service.createPrintJob();


PrintJobWatcher pjw = new PrintJobWatcher(job);
job.print(doc, pras);
pjw.waitForDone();
in.close();

// send FF to eject the page


InputStream ff = new ByteArrayInputStream("\f".getBytes());
Doc docff = new SimpleDoc(ff, flavor, null);
DocPrintJob jobff = service.createPrintJob();
pjw = new PrintJobWatcher(jobff);
jobff.print(docff, null);
pjw.waitForDone();
}
}

class PrintJobWatcher {
boolean done = false;

PrintJobWatcher(DocPrintJob job) {
job.addPrintJobListener(new PrintJobAdapter() {
public void printJobCanceled(PrintJobEvent pje) {
allDone();
}
public void printJobCompleted(PrintJobEvent pje) {
allDone();
}
public void printJobFailed(PrintJobEvent pje) {
allDone();
}
public void printJobNoMoreEvents(PrintJobEvent pje) {
allDone();
}
void allDone() {
synchronized (PrintJobWatcher.this) {
done = true;
System.out.println("Printing done ...");
PrintJobWatcher.this.notify();
}

Print a text file using the javax.print API 275


Real's HowTo PDF version

}
});
}
public synchronized void waitForDone() {
try {
while (!done) {
wait();
}
} catch (InterruptedException e) {
}
}
}

To print a String, see this HowTo

Print a String using the javax.print API


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-print-a-string-using-javax-print-api.html

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;

import javax.print.Doc;
import javax.print.DocFlavor;
import javax.print.DocPrintJob;
import javax.print.PrintException;
import javax.print.PrintService;
import javax.print.PrintServiceLookup;
import javax.print.SimpleDoc;

import javax.print.attribute.HashPrintRequestAttributeSet;
import javax.print.attribute.PrintRequestAttributeSet;
import javax.print.attribute.standard.Copies;

import javax.print.event.PrintJobAdapter;
import javax.print.event.PrintJobEvent;

public class PrintText {

public static void main(String[] args) throws PrintException, IOException {

String defaultPrinter =
PrintServiceLookup.lookupDefaultPrintService().getName();
System.out.println("Default printer: " + defaultPrinter);
PrintService service = PrintServiceLookup.lookupDefaultPrintService();

// prints the famous hello world! plus a form feed


InputStream is = new ByteArrayInputStream("hello world!\f".getBytes("UTF8"));

Print a String using the javax.print API 276


Real's HowTo PDF version

PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();


pras.add(new Copies(1));

DocFlavor flavor = DocFlavor.INPUT_STREAM.AUTOSENSE;


Doc doc = new SimpleDoc(is, flavor, null);
DocPrintJob job = service.createPrintJob();

PrintJobWatcher pjw = new PrintJobWatcher(job);


job.print(doc, pras);
pjw.waitForDone();
is.close();
}
}

class PrintJobWatcher {
boolean done = false;

PrintJobWatcher(DocPrintJob job) {
job.addPrintJobListener(new PrintJobAdapter() {
public void printJobCanceled(PrintJobEvent pje) {
allDone();
}
public void printJobCompleted(PrintJobEvent pje) {
allDone();
}
public void printJobFailed(PrintJobEvent pje) {
allDone();
}
public void printJobNoMoreEvents(PrintJobEvent pje) {
allDone();
}
void allDone() {
synchronized (PrintJobWatcher.this) {
done = true;
System.out.println("Printing done ...");
PrintJobWatcher.this.notify();
}
}
});
}
public synchronized void waitForDone() {
try {
while (!done) {
wait();
}
} catch (InterruptedException e) {
}
}
}

To print a text file, see this HowTo

Print a String using the javax.print API 277


Real's HowTo PDF version

Print text to a printer easily


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0051.html

A quick and simple way to output some text to a printer is to print to OS logical device attached a printer.

For example, on a Windows machine :

import java.io.FileWriter;

public class SimplePrinting {


public static void main(String[] args) {
try {
FileWriter out = new FileWriter("lpt1");
out.write("Hello world");
out.write(0x0D); // CR
out.close();
}
catch (IOException e) {
e.printStackTrace();
}
}
}

Print without a Dialog


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0350.html

JobAttributes theJobAttribs = new JobAttributes();


PageAttributes thePageAttribs = new PageAttributes();

theJobAttribs.setDialog(JobAttributes.DialogType.NONE);
theJobAttribs.setPrinter("HP DeskJet 610C"); // the printer to be used
PrintJob myJob = getToolkit().getPrintJob(this, "PrintJob", theJobAttribs, thePageAttribs);

if (myJob != null) {
Graphics g = myJob.getGraphics();
if (g != null) {
String s = myArea.getText(); // what you like to print
printText(myJob, g, s);
g.dispose();
}
}
myJob.end();

Print text to a printer easily 278


Real's HowTo PDF version

Initialize and write to a serial port


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0062.html

This is for JAVA application only (JDK1.1).

(Win)Initialization is done via the MODE.COM utility. Then to write, simply open a stream using the OS
logical name attached to the serial port. You can use the same technique to print to the printer port (in this
case the local name would be "LPTx:").

public class SerialTest {


public static void main( String args[]) {
Runtime rt = Runtime.getRuntime();
Process p = null;
String portname = "com1:";
// for Win95 : c:\\windows\\command.com
// c:\\windows\\command\\mode.com
String cmd[] = {
"c:\\winnt\\system32\\cmd.exe", "/c",
"start", "/min",
"c:\\winnt\\system32\\mode.com", portname,
"baud=9600", "parity=n", "data=8",
"stop=1",
};
try {
p = rt.exec( cmd );
if( p.waitFor() != 0 ) {
System.out.println("Error executing command: " + cmd );
System.exit( -1 );
}
byte data[] =
"Writing a byte stream out of a serial port.".getBytes();
FileOutputStream fos = new FileOutputStream( portname );
BufferedOutputStream bos = new BufferedOutputStream( fos );
fos.write( data, 0, data.length );
fos.close();
}
catch( Exception e ) {
e.printStackTrace();
}
}
}

Open or close a CD/DVD drive


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0574.html

Initialize and write to a serial port 279


Real's HowTo PDF version

Java provides no way to interact with a cd drive.

One easy way on the Windows plateform is to call a VBS script.

In this HowTo, we are creating a temporary vbs file and execute it. This technique is useful to do something
that a regular Java can't do because it's too specific to OS where the Java is running. The vbs file is created
in the "temporary" folder and is deleted by the JVM at the end.

import java.io.File;
import java.io.FileWriter;

public class CDUtils {


private CDUtils() { }

public static void open(String drive) {


try {
File file = File.createTempFile("realhowto",".vbs");
file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);
String vbs = "Set wmp = CreateObject(\"WMPlayer.OCX\") \n"
+ "Set cd = wmp.cdromCollection.getByDriveSpecifier(\""
+ drive + "\") \n"
+ "cd.Eject";
fw.write(vbs);
fw.close();
Runtime.getRuntime().exec("wscript " + file.getPath()).waitFor();
// thanks to TrueJavaProgammer for the waitFor() tip!
// Runtime.getRuntime().exec("wscript " + file.getPath()).waitFor();
// Thread.sleep(2000);
}
catch(Exception e){
e.printStackTrace();
}
}

public static void close(String drive) {


try {
File file = File.createTempFile("realhowto",".vbs");
file.deleteOnExit();
FileWriter fw = new FileWriter(file);
// to close a CD, we need eject two times!
String vbs = "Set wmp = CreateObject(\"WMPlayer.OCX\") \n"
+ "Set cd = wmp.cdromCollection.getByDriveSpecifier(\""
+ drive + "\") \n"
+ "cd.Eject \n "
+ "cd.Eject ";
fw.write(vbs);
fw.close();
Runtime.getRuntime().exec("wscript " + file.getPath()).waitFor();
// thanks to TrueJavaProgammer for the waitFor() tip!
// Runtime.getRuntime().exec("wscript "+ file.getPath());
// Thread.sleep(2000);

Open or close a CD/DVD drive 280


Real's HowTo PDF version

}
catch(Exception e){
e.printStackTrace();
}
}

public static void main(String[] args){


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, "Press OK to open CD", "CDUtils",
javax.swing.JOptionPane.DEFAULT_OPTION);
CDUtils.open("D:\\");
javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, "Press OK to close CD", "CDUtils",
javax.swing.JOptionPane.DEFAULT_OPTION);
CDUtils.close("D:\\");
}
}

NOTE : Windows Media Player version 7 or later is required

Get the volume label


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0455.html

This will retrieve the hard disk volume label :

import java.io.*;
import javax.swing.filechooser.*;

public class VolumeLabel {


private VolumeLabel() { }

public static void main(String[] args) {


System.out.println("\"" + get(args[0]) + "\"");
}

public static String get(String path) {


FileSystemView view = FileSystemView.getFileSystemView();
File dir = new File(path);
String name = view.getSystemDisplayName(dir);
if (name == null) { return null; }
name = name.trim();
if (name == null || name.length() < 1) {
return null;
}
int index = name.lastIndexOf(" (");
if (index > 0) {
name = name.substring(0, index);
}
return name;

Get the volume label 281


Real's HowTo PDF version

}
}

The output

Running from c:\temp

>java VolumeLabel c:
"temp"

>java VolumeLabel c:\


"HARDDISK1"

Detect the storage device type


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0635.html

javax.swing.filechooser.FileSystemView provides a way to detect the type of a particular device.

import java.io.File;
import java.util.Arrays;
import java.util.List;
import javax.swing.filechooser.FileSystemView;

public class Test2 {


public static void main(String args[]){
List <File>files = Arrays.asList(File.listRoots());
for (File f : files) {
String s = FileSystemView.getFileSystemView().getSystemTypeDescription(f);
System.out.println("*" + s);
}
/* output (French WinXP)

*Disquette 3½ pouces
*Disque local
*Lecteur CD
*Disque local
*/
}
}

As you can see the output is localized (from the OS).

The following output the name or label of the storage device :

import java.io.File;
import java.util.Arrays;
import java.util.List;

Detect the storage device type 282


Real's HowTo PDF version

import javax.swing.filechooser.FileSystemView;

public class Test2 {


public static void main(String args[]){
List <File>files = Arrays.asList(File.listRoots());
for (File f : files) {
String s = FileSystemView.getFileSystemView().getSystemDisplayName(f);
System.out.println("*" + s);
}
/* output (French WinXP)

*
*REGA1 (C:)
*
*My Book (F:)
*/

}
}

Turn on MQ Debug mode


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-turn-on-mq-debug-mode.html

Websphere MQ exposes many properties to control debugging inforation output. See this document.

When starting the JRE, set the properties on the command line. For example :

-Dcom.ibm.msg.client.commonservices.trace.status=ON
-Dcom.ibm.msg.client.commonservices.trace.outputName=C:\myapps\logs\mq.log

will make the MQ client to produce a log with a lot of information.

Version information in main body of trace


TimeStamp TID ObjectId Class
=============================================================================================
15:04:32.833.00 0001 static c.i.m.c.commonservices.trace.Trace
15:04:32.833.01 0001 static c.i.m.c.commonservices.componentmanager.ComponentManager
15:04:32.833.02 0001 @14a18d c.i.m.c.commonservices.componentmanager.ComponentManager(Co
...

Get faster console output (System.out.println() replacement)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0603.html

Turn on MQ Debug mode 283


Real's HowTo PDF version

If your program is doing a lot printing to the console using System.out.println() then it is possible to get a
good performance boost by using an alternative to do the console output.

By default, System.out.print() is only line-buffered and does a lot work related to Unicode handling.
Because of its small buffer size, System.out.println() is not well suited to handle many repetitive outputs in
a batch mode. Each line is flushed right away. If your output is mainly ASCII-based then by removing the
Unicode-related activities, the overall execution time will be better.

Consider this program :

import java.io.BufferedWriter;
import java.io.FileDescriptor;
import java.io.FileOutputStream;
import java.io.OutputStreamWriter;

public class Test {


public static void main(String...args) throws Exception {
long start = System.currentTimeMillis();
for (int i = 0; i < 1000000; i++) {
System.out.print("abcdefghijk ");
System.out.print(String.valueOf(i));
System.out.print('\n');
}
System.err.println("Loop time: " +
(System.currentTimeMillis() - start));
}
}

The result is

>java Test >NUL


Loop time: 7000

Now, rewrite this program to use a 512-bytes buffer and specify the ASCII as character-encoding to be
used.

import java.io.BufferedWriter;
import java.io.FileDescriptor;
import java.io.FileOutputStream;
import java.io.OutputStreamWriter;

public class Test {


public static void main(String...args) throws Exception {
BufferedWriter out = new BufferedWriter(new OutputStreamWriter(new
FileOutputStream(java.io.FileDescriptor.out), "ASCII"), 512);
long start = System.currentTimeMillis();
for (int i = 0; i < 1000000; i++) {
out.write("abcdefghijk ");
out.write(String.valueOf(i));
out.write('\n');

Get faster console output (System.out.println() replacement) 284


Real's HowTo PDF version

}
out.flush();
System.err.println("Loop time: " +
(System.currentTimeMillis() - start));
}

The result is

>java Test >NUL


Loop time: 672

Note that your result will vary depending on your machine/java version but the performance gain should in
the same magnitude.

Simple input from the keyboard


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0053.html

First method

import java.io.*;
public class TestReadLine {
public static void main (String args[]) {
StreamTokenizer Input=new StreamTokenizer(System.in);
try {
System.out.print(" Your first name : ");
Input.nextToken();
System.out.println("Hi " + Input.sval + "!");
}
catch (Exception e) {
e.printStackTrace();
}
}
}

Second method JDK1.0.2

java.io.DataInputStream in =
new java.io.DataInputStream(System.in);
String aLine = in.readLine();

Third method JDK1.1


In you program, use EasyInput.inputStr("<prompt>") to input a String or EasyInput.InputInt("<prompt>")
for an integer.

Simple input from the keyboard 285


Real's HowTo PDF version

public class EasyInput {


public static int inputInt(String s) {
BufferedReader input =
new BufferedReader(new InputStreamReader(System.in));
System.out.print(s);
int i =0;
try {
i = Integer.parseInt(input.readLine());
}
catch (Exception e) {
e.printStackTrace();
}
return i;
}

public static String inputStr(String s) {


String aLine = "";
BufferedReader input =
new BufferedReader(new InputStreamReader(System.in));
System.out.print(s);
try {
aLine = input.readLine();
}
catch (Exception e) {
e.printStackTrace();
}
return aLine;
}

public static void main(String s[]) {


while(true) {
int y = inputInt(" Year: ");
int m = inputInt("Month: ");
int d = inputInt(" Day: ");
String you = inputStr("Your name: ");
System.out.println(you + " " + y + m + d);
}
}
}

NOTE: JDK 1.5 provides the Scanner class to do this, see this HowTo.

Output french character to the console


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0046.html

Output french character to the console 286


Real's HowTo PDF version

Java 1.6 or more

In Java 1.6 you can use System.console() instead of System.out.println() to display accentuated characters to
console.

public class Test2 {


public static void main(String args[]){
String s = "caractères français : à é \u00e9"; // Unicode for "é"
System.out.println(s);
System.console().writer().println(s);
}
}

anf the output is

C:\temp>java Test
caractþres franþais : Ó Ú Ú
caractères français : à é é

Java 1.5 or less

When starting the JVM and pass on the command line the default file encoding to be used. Then you will
be able to use regular System.out.println().

java -Dfile.encoding=Cp850 MyApp

Another way is to specify in the code the encoding to be used.

import java.io.*;

public class Test {


public static void main(String[] args) {
PrintStream ps = null;
String javaString =
"caractères français : à é \u00e9"; // Unicode for "é"

try {
ps = new PrintStream(System.out, true, "Cp850");
}
catch (UnsupportedEncodingException error) {
System.err.println(error);
System.exit(0);
}
ps.println(javaString);
}
}

Note : List of supported encodings here

Output french character to the console 287


Real's HowTo PDF version

Clear the console and control attributes


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0047.html

There is no built-in way to really control character-based application in Java.

To clear the screen, you can use many System.out.println();, that's about it!

for (int i=0; i<25; i++)


System.out.println();

... Or use some JNI functions, see this HowTo.

While it is possible to use the DOS ANSI.SYS driver with Windows 9x and make old JVM use it ... it won't
work with modern Windows installations. Windows NT (or better) CMD.EXE does not support ANSI
escape sequences at all.

Fortunately many Open Source solutions are coming to the rescue and Jansi and JCurses are two of them.

Jansi

Jansi is a small java library that allows you to use ANSI escape sequences to format your console output
which works even on Windows.

import org.fusesource.jansi.AnsiConsole;

public class Test {


public static final String ANSI_CLS = "\u001b[2J";
public static final String ANSI_HOME = "\u001b[H";
public static final String ANSI_BOLD = "\u001b[1m";
public static final String ANSI_AT55 = "\u001b[10;10H";
public static final String ANSI_REVERSEON = "\u001b[7m";
public static final String ANSI_NORMAL = "\u001b[0m";
public static final String ANSI_WHITEONBLUE = "\u001b[37;44m";

public static void main(String args[]){


AnsiConsole.systemInstall();
AnsiConsole.out.println(ANSI_CLS);
AnsiConsole.out.println
(ANSI_AT55 + ANSI_REVERSEON + "Hello world" + ANSI_NORMAL);
AnsiConsole.out.println
(ANSI_HOME + ANSI_WHITEONBLUE + "Hello world" + ANSI_NORMAL);
AnsiConsole.out.print
(ANSI_BOLD + "Press a key..." + ANSI_NORMAL);
try {System.in.read();}catch(Exception e){}
AnsiConsole.out.println(ANSI_CLS);
AnsiConsole.systemInstall();

Clear the console and control attributes 288


Real's HowTo PDF version

}
}

NOTE: Check this "old" text file to have an overview of ANSI Escape Sequences.

The above example shows that it's possible to use ANSI codes directly but Jansi provides a neat mechanism
to help building the required ANSI sequence.

import static org.fusesource.jansi.Ansi.*;


import static org.fusesource.jansi.Ansi.Color.*;
...
System.out.println( ansi().eraseScreen().fg(RED).a("Hello").fg.(GREEN).a(" World").reset()

Jansi works on Linux32/64, Windows 32/64 and OS/X.

JCurses

The Java Curses Library (JCurses) is a library for developing text terminal based applications using Java
programming language. It is implemented as a Windowing toolkit similar to AWT, but built upon the
UNIX "curses" windowing system.

JCurses works on Unix and Windows (32 bit only, on a 64-bit OS you need to use JCurses with a 32-bit
JVM).

This example will display a character-based window with a label, a textfield and a button (don't click with
you mouse, use the keyboard!).

import jcurses.system.*;
import jcurses.widgets.*;
import jcurses.util.*;
import jcurses.event.*;

public class Test2 extends Window implements ItemListener, ActionListener,


ValueChangedListener, WindowListener, WidgetsConstants {
static Test2 window = null;
static TextField textfield = null;
static Button button = null;

public Test2(int width, int height) {


super(width, height, true, "JCurses Test");
}

public static void main(String[] args) throws Exception {


window = new Test2(30, 20);
window.init();
}

public void init() {


DefaultLayoutManager mgr = new DefaultLayoutManager();
mgr.bindToContainer(window.getRootPanel());

Clear the console and control attributes 289


Real's HowTo PDF version

mgr.addWidget(
new Label("Hello World!",
new CharColor(CharColor.WHITE, CharColor.GREEN)),
0, 0, 20, 10,
WidgetsConstants.ALIGNMENT_CENTER,
WidgetsConstants.ALIGNMENT_CENTER);

textfield = new TextField(10);


mgr.addWidget(textfield, 0, 0, 20, 20,
WidgetsConstants.ALIGNMENT_CENTER,
WidgetsConstants.ALIGNMENT_CENTER);

button = new Button("Quit");


mgr.addWidget(button, 0, 0, 20, 30,
WidgetsConstants.ALIGNMENT_CENTER,
WidgetsConstants.ALIGNMENT_CENTER);

button.setShortCut('q');
button.addListener(this);
window.addListener((WindowListener) this);
window.show();
}

public void actionPerformed(ActionEvent event) {


Widget w = event.getSource();
if (w == button) {
new Message("HowTo", "You are about to quit", "OK").show();
window.close();
}
}

public void stateChanged(ItemEvent e) { }

public void valueChanged(ValueChangedEvent e) { }

public void windowChanged(WindowEvent event) {


if (event.getType() == WindowEvent.CLOSING) {
event.getSourceWindow().close();
// Toolkit.clearScreen(new CharColor(CharColor.WHITE, CharColor.BLACK));
}
}
}

Easy keyboard input (JDK1.5)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0491.html

import java.util.Scanner;

Easy keyboard input (JDK1.5) 290


Real's HowTo PDF version

class TestScanner {
public static void main(String args[]) {
Scanner sc = new Scanner(System.in);
System.out.println(sc.nextLine());
System.out.println("Done");
}
}

A Scanner breaks its input into tokens using a delimiter pattern, which by default matches whitespace. The
resulting tokens may then be converted into values of different types using the various next methods.

import java.util.Scanner;

class TestScanner {
public static void main(String args[]) {
// if input is
// 10,12
// then the output is
// 10
// 12
//
// we use a regex as delimiter to combine "," and
// whitespace (in this case the ENTER key)
Scanner sc = new Scanner(System.in).useDelimiter("[,\\s]");
while (sc.hasNextInt()) {
int i = sc.nextInt();
System.out.println(i);
}
System.out.println("Done");
}
}

Scanner can be used with String or Stream. For exemple, the above HowTo can be written like this :

import java.util.Scanner;

class TestScanner {
public static void main(String args[]) {
String input = "10,12"
Scanner sc = new Scanner(System.in).useDelimiter(",");
while (sc.hasNextInt()) {
int i = sc.nextInt();
System.out.println(i);
}
System.out.println("Done");
}
}

Easy keyboard input (JDK1.5) 291


Real's HowTo PDF version

Force keyboard input in CAPS LOCK on


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0643.html

import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;

import javax.swing.JFrame;
import javax.swing.JTextField;

public class Test {

private JFrame myFrame;


private JTextField myTextField;

public void doit() {


myFrame = new JFrame();
myFrame.setSize(400, 200);
myFrame.setLocation(100, 100);
myFrame.setLayout(new java.awt.FlowLayout());
myTextField = new JTextField(20);
// Keyboard is CAPSLOCK ON
java.awt.Toolkit.getDefaultToolkit()
.setLockingKeyState(KeyEvent.VK_CAPS_LOCK, true);
myFrame.add(myTextField);
myFrame.addWindowListener( new WindowAdapter() {
public void windowOpened( WindowEvent e ){
myTextField.requestFocus();
}
public void windowActivated( WindowEvent e ){
boolean focus = myTextField.requestFocusInWindow();
if(focus){
System.out.println("Focus successful");
}
else{
System.out.println("Focus unsuccessful");
}
}
}
);
myFrame.setVisible(true);
}

public static void main(String args[]) {


new Test().doit();
}
}

Force keyboard input in CAPS LOCK on 292


Real's HowTo PDF version

NOTE : This technique changes the keyboard state so the effect is also seen outside the Java program.

See also this related Howto.

Automatic conversion of System.out output


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-automatic-conversion-of-System.out-output.html

• Convert System.out output to uppercase.


import java.io.PrintStream;

public class Test {


public static void main(String[] args) throws Exception {

System.setOut(new PrintStream(System.out) {
public void println(String s) {
super.println(s.toUpperCase());
}
});

System.out.println("hello world"); // output : HELLO WORLD


}
}
• Replace the regular output stream of System.out to do useful thing like implementing a Tee mechanism to
output to the console and to file.
import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintStream;

public class TeeOutputStream extends OutputStream {


private OutputStream os1;
private OutputStream os2;

public TeeOutputStream(OutputStream os1, OutputStream os2) {


this.os1 = os1;
this.os2 = os2;
}

public void write(int i) throws IOException {


os1.write(i);
os2.write(i);
}

public void flush() throws IOException {


os1.flush();
os2.flush();
}
public void close() throws IOException {
os1.close();

Automatic conversion of System.out output 293


Real's HowTo PDF version

os2.close();
}

public static void main(String[] args) throws IOException {


System.out.println("Starting...");
// keep the original
PrintStream originalOutStream = System.out;
System.setOut(
new PrintStream(
new TeeOutputStream(
System.out,
new PrintStream("C:/temp/howto.out"))));
// restore the original

System.out.println("*");
for (int i = 1; i<= 10; i++) {
System.out.println(i);
}
System.out.println("*");

System.setOut(originalOutStream);
System.out.println("Done. Check the log");
}
}

Execute an external program and capture the output


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0014.html

Be sure to read this Javaworld article. It describes the various pitfalls related to the Runtime.exec()
method.

Using Runtime.exec()

This example will capture the output (from stdio) of an external program.

package com.rgagnon.howto;

import java.io.*;

public class Exec {


public static void main(String args[]) {
try {
String line;
Process p = Runtime.getRuntime().exec("cmd /c dir");
BufferedReader bri = new BufferedReader
(new InputStreamReader(p.getInputStream()));
BufferedReader bre = new BufferedReader

Execute an external program and capture the output 294


Real's HowTo PDF version

(new InputStreamReader(p.getErrorStream()));
while ((line = bri.readLine()) != null) {
System.out.println(line);
}
bri.close();
while ((line = bre.readLine()) != null) {
System.out.println(line);
}
bre.close();
p.waitFor();
System.out.println("Done.");
}
catch (Exception err) {
err.printStackTrace();
}
}
}

The next example, launch CMD.EXE, grab stdin/stdout and push to stdin command to be interpreted by the
shell.

String line;
OutputStream stdin = null;
InputStream stderr = null;
InputStream stdout = null;

// launch EXE and grab stdin/stdout and stderr


Process process = Runtime.getRuntime ().exec ("/folder/exec.exe");
stdin = process.getOutputStream ();
stderr = process.getErrorStream ();
stdout = process.getInputStream ();

// "write" the parms into stdin


line = "param1" + "\n";
stdin.write(line.getBytes() );
stdin.flush();

line = "param2" + "\n";


stdin.write(line.getBytes() );
stdin.flush();

line = "param3" + "\n";


stdin.write(line.getBytes() );
stdin.flush();

stdin.close();

// clean up if any output in stdout


BufferedReader brCleanUp =
new BufferedReader (new InputStreamReader (stdout));
while ((line = brCleanUp.readLine ()) != null) {
//System.out.println ("[Stdout] " + line);
}
brCleanUp.close();

Execute an external program and capture the output 295


Real's HowTo PDF version

// clean up if any output in stderr


brCleanUp =
new BufferedReader (new InputStreamReader (stderr));
while ((line = brCleanUp.readLine ()) != null) {
//System.out.println ("[Stderr] " + line);
}
brCleanUp.close();

Launch a Windows CMD (or BAT) file and retrieve the errorlevel or exitcode

// win xp
import java.io.*;
public class CmdExec {
public static void main(String argv[]) {
try {
String line;
Process p = Runtime.getRuntime().exec("test.cmd");
p.waitFor();
System.out.println(p.exitValue());
}
catch (Exception err) {
err.printStackTrace();
}
}
}

test.cmd (set the errorlevel manually)

@echo hello world


@exit 42

test.cmd (set the errorlevel 1 (problem detected)

@java -garbage

test.cmd (set the errorlevel 0 (execution Ok)

@java -version

Launch a Unix script

String[] cmd = {"/bin/sh", "-c", "ls > hello"};


Runtime.getRuntime().exec(cmd);

Using the ProcessBuilder

Since 1.5, the ProcessBuilder class provides more controls overs the process to be started. It's possible to
set a starting directory.

import java.io.*;

Execute an external program and capture the output 296


Real's HowTo PDF version

import java.util.*;

public class CmdProcessBuilder {


public static void main(String args[])
throws InterruptedException,IOException
{
List<String> command = new ArrayList<String>();
command.add(System.getenv("windir") +"\\system32\\"+"tree.com");
command.add("/A");

ProcessBuilder builder = new ProcessBuilder(command);


Map<String, String> environ = builder.environment();
builder.directory(new File(System.getenv("temp")));

System.out.println("Directory : " + System.getenv("temp") );


final Process process = builder.start();
InputStream is = process.getInputStream();
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
while ((line = br.readLine()) != null) {
System.out.println(line);
}
System.out.println("Program terminated!");
}
}

Windows rundll32 utility

Windows File association


Any program using the Windows file association mechanism can be started with the rundll32 utility.

// "file" is the filename of the data file


// ex. myresume.doc
// to start Word if the doc extension is associated with it.
Runtime.getRuntime().exec
("rundll32 SHELL32.DLL,ShellExec_RunDLL " + file.getAbsolutePath());

See also this HowTo about the new Desktop API, the recommended solution (but you need JDK1.6).
See also this one to open the default browser.

The following example start a Dial-up connection on the Win plateform :

[Dialup.java]
public class Dialup {
public static void main(String[] args) throws Exception {
Process p = Runtime.getRuntime()
.exec("rundll32.exe rnaui.dll,RnaDial MyConnection");
p.waitFor();
System.out.println("Done.");
}
}

Execute an external program and capture the output 297


Real's HowTo PDF version

The "MyConnection" is the DUN and it's case sensitive.

You still need to press ENTER to CONNECT, there is an option in the Connection properties to connect
automatically.

On NT and W2K, rnaui.dll is not available. Use rasdial.exe instead.

rasdial "connection name"


rasdial "connection name" /d to drop
rasdial /? for more options

PDF (Windows only)

public class ShowPDF {


public static void main(String[] args) throws Exception {
Process p =
Runtime.getRuntime()
.exec("rundll32 url.dll,FileProtocolHandler c:/pdf/mypdf.pdf");
p.waitFor();
System.out.println("Done.");
}
}

PDF (Mac only)

public class ShowPDF {


public static void main (String[] args) throws Exception{
Process p = Runtime.getRuntime().exec("open /Documents/mypdf.pdf");
}
}

More runddl32 examples

Path to executable with spaces in them

You can include a path for the program to be executed. On the Win plateform, you need to put the path in
quotes if the path contains spaces.

public class Test {


public static void main(String[] args) throws Exception {
Process p = Runtime.getRuntime().exec(
"\"c:/program files/windows/notepad.exe\"");
p.waitFor();
}
}

If you need to pass arguments, it's safer to a String array especially if they contain spaces.

String[] cmd = { "myProgram.exe", "-o=This is an option" };


Runtime.getRuntime().exec(cmd);

Execute an external program and capture the output 298


Real's HowTo PDF version

If using the start command and the path of the file to be started contains a space then you must specified a
title to the start command.

String fileName = "c:\\Applications\\My Documents\\test.doc";


String[] commands = {"cmd", "/c", "start", "\"DummyTitle\"",fileName};
Runtime.getRuntime().exec(commands);

VBSCRIPT

// Win9x
Runtime.getRuntime().exec("start myscript.vbs");

// WinNT
Runtime.getRuntime().exec("cmd /c start myscript.vbs");

or

// with a visible console


Runtime.getRuntime().exec("cscript myscript.vbs");

// with no visible console


Runtime.getRuntime().exec("wscript myscript.vbs");

HTML Help (Windows only)

Runtime.getRuntime().exec("hh.exe myhelpfile.chm");

Start Excel

import java.io.IOException;

class StartExcel {
public static void main(String args[])
throws IOException
{
Runtime.getRuntime().exec("cmd /c start excel.exe");
}
}

To load a worksheet

import java.io.IOException;

class StartExcel {
public static void main(String args[])
throws IOException
{
String fileName = "c:\\temp\\xls\\test2.xls";
String[] commands = {"cmd", "/c", "start", "\"DummyTitle\"",fileName};
Runtime.getRuntime().exec(commands);
}
}

Execute an external program and capture the output 299


Real's HowTo PDF version

It's important to pass a dummy title to the Windows start command where there is a possibility that the
filename contains a space. It's a feature.

Start a Windows application under another account

You use the RUNAS command from the command line to start an application under another account (not
available with XP Home edition). There are many switches that can enhance the behaviour of RUNAS.
Typing "runas /?" from the command prompt gets you all the options.

String commands [] = new String [] {


"CMD.EXE",
"/C",
"RUNAS /profile /savecred /user:"
+ "administrator"
+ " " + "regedit.exe"
};

Runtime.getRuntime().exec(commands);

/SaveCred option allows you to save a password for that account and then reuse it later. For example,
The command runas /savecred /user:administrator regedit.exe prompts for the
password, and then Regedit runs. Next time you use the same command, there is no password prompt.

One potential problem is that when /SaveCred saves the credentials it saves it for whenever RUNAS
invokes that user account. This can be a huge security risk so be careful using it!

RUNAS capability can be disabled by editing the Registry or by disabling the RUNAS or Secondary Logon
Services. The appropriate registry key is
HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\policies\Explorer, create a
new DWORD value named HideRunAsVerb and assign it a value of 1 to disable Run as.

RUNAS doesn't work when used from a Windows service.

Windows : execute something in Program Files

We want to execute the textpad editor located in C:\Program Files\TextPad 4 but without hard coding the
path since it can be different for a localized version of Windows.

We simply extract to environnment variable called %programfiles% and build the complete path from
there.

[JDK1.5]

public class Exec {


static String WIN_PROGRAMFILES = System.getenv("programfiles");
static String FILE_SEPARATOR = System.getProperty("file.separator");

public static void main(String[] args) throws Exception {

Execute an external program and capture the output 300


Real's HowTo PDF version

String[] commands =
{"cmd.exe",
"/c",
WIN_PROGRAMFILES
+ FILE_SEPARATOR
+ "textpad 4"
+ FILE_SEPARATOR + "textpad.exe"};
Runtime.getRuntime().exec(commands);
}
}

NOTE : Prior Vista, System folders were localized on disk like C:\Program Files -> C:\Archivos de
programa on the Windows with the Spanish localization. Since Vista, System Folders always exists with
the english name BUT when viewed through Explorer, the localized name is shown. See
http://msmvps.com/blogs/carlosq/archive/2007/02/12/windows-vista-junctions-points-mui-and-localized-folder-nam

Launch the application associated with a file extension


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0579.html

JDK1.6
The java.awt.Desktop class uses your host operating system's file associations to launch applications
associated with specific file types.

First it's a good idea to check if the Desktop operations are supported on the running plateform.

import java.awt.*;
...

if (Desktop.isDesktopSupported()) {
Desktop desktop = Desktop.getDesktop();
for (Desktop.Action action : Desktop.Action.values()) {
System.out.println("action " + action + " supported? "
+ desktop.isSupported(action));
}
}

The possible actions are


• BROWSE. launching the user-default browser to show a specified URI
• MAIL. launching the user-default mail client with an optional mailto URI;
• OPEN. launching a registered application to open a specified file.
• EDIT. launching a registered application to edit a specified file.
• PRINT. launching a registered application to print a specified file.

then

Launch the application associated with a file extension 301


Real's HowTo PDF version

// application associated to a file extension


public static void open(File document) throws IOException {
Desktop dt = Desktop.getDesktop();
dt.open(document);
}

public static void print(File document) throws IOException {


Desktop dt = Desktop.getDesktop();
dt.print(document);
}

// default browser
public static void browse(URI document) throws IOException {
Desktop dt = Desktop.getDesktop();
dt.browse(document);
}

// default mail client


// use the mailto: protocol as the URI
// ex : mailto:[email protected]?SUBJECT=Love me tender&BODY=love me sweet
public static void mail(URI document) throws IOException {
Desktop dt = Desktop.getDesktop();
dt.mail(document);
}

See the javadoc at http://java.sun.com/javase/6/docs/api/java/awt/Desktop.html

See also this HowTo and this one.

Launch an application from another application


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0394.html

While you can exec("java myanotherapp"), it is more appropriate to instanciate and called the main method
of the other application.

For example, take this simple application :

public class Program2 {


public static void main(String arg[]) {
System.out.println("Hello from Program2");
}
}

To call the above application from another

public class Program1a {


public static void main(String arg[]) {

Launch an application from another application 302


Real's HowTo PDF version

System.out.println("Hello from Program1a");


new Thread(){
public void run() {
Program2.main(new String[]{});}
}.start();
}

The above example is used when the class is hard-coded.

The dynamic version is little more tricky.

public class Program1b {


public static void main(String arg[]) {
System.out.println("Hello from Program1b");
new Program1b().execute("Program2");
}

public void execute(String name) {


Class params[] = {String[].class};
// if you need parameters
// String[] args = new String[] { "Hello", "world" };
// Class params[] = new Class[] { args.getClass() });
try {
Class.forName(name).
getDeclaredMethod("main", params).
invoke(null, new Object[] {new String[] {}});
}
catch(Exception e){ e.printStackTrace();}
}
}

Launch many programs using Thread and use join() to wait for the completion.

[Program2.java]
public class Program2 {
public static void main(String arg[]) {
System.out.println("Hello from Program2");
System.out.println("Hello from Program2");
System.out.println("Hello from Program2");
System.out.println("Hello from Program2");
}
}

[Program1a.java]
public class Program1a {
public static void main(String arg[]) throws Exception{
System.out.println("Hello from Program1a");
Thread t1 = new Thread(){
public void run() {
Program2.main(new String[]{});}
};

Launch an application from another application 303


Real's HowTo PDF version

t1.start();
t1.join();
System.out.println("Hello from Program1a");
}
}

The output :

C:\>java Program1a
Hello from Program1a
Hello from Program2
Hello from Program2
Hello from Program2
Hello from Program2
Hello from Program1a

Start the default browser from an application


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0071.html

In this snippet, we initialize a Listbox from a file containing some URLs. When we double click an item,
the default browser is started with the selected HTML page as parameter. This example is Windows
oriented since I have used the start command which supports the file association.

[urlList.txt]

http://www.rgagnon.com/javadetails/java-0001.html|JAVA How-to 1
http://www.rgagnon.com/javadetails/java-0002.html|JAVA How-to 2
http://www.rgagnon.com/javadetails/java-0003.html|JAVA How-to 3
http://www.rgagnon.com/javadetails/java-0004.html|JAVA How-to 4
http://www.rgagnon.com/javadetails/java-0005.htmL|JAVA How-to 5

[StartBrowser.java]

import java.applet.*;
import java.awt.*;
import java.awt.event.*;
import java.net.*;
import java.io.*;

public class StartBrowser {


public static void main(String s[]) {
AFrame f = new AFrame();
}
}

class AFrame extends Frame implements ActionListener {


List lbx;

Start the default browser from an application 304


Real's HowTo PDF version

String url[] = new String[50];

public AFrame() {
// dispaly setup
setTitle("URL selection");
setSize(400,400);
lbx = new List();
add(lbx);
initLbx();
// action on listbox double click
lbx.addActionListener(this);
// to close the Frame
addWindowListener
(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
}
);
setVisible(true);
}

public void actionPerformed (ActionEvent ae) {


String theUrl = url[lbx.getSelectedIndex()];
// start the default browser (Win95 platform)
// on listbox double click

String cmdLine = "start " + theUrl;


// on NT, you need to start cmd.exe because start is not
// an external command but internal, you need to start the
// command interpreter
// String cmdLine = "cmd.exe /c " + cmdLine;
try {
Process p = Runtime.getRuntime().exec(cmdLine);
}
catch (Exception e) {
e.printStackTrace();
}
}

public void initLbx() {


int i = 0;
try {
String aLine = "";
BufferedReader in
= new BufferedReader(new FileReader("urlList.txt"));
while(null != (aLine = in.readLine())) {
java.util.StringTokenizer st =
new java.util.StringTokenizer(aLine, "|");
url[i++] = st.nextToken();
lbx.addItem(st.nextToken());
// lbx.add(st.nextToken()); in JDK1.2
}
}

Start the default browser from an application 305


Real's HowTo PDF version

catch(Exception e) {
e.printStackTrace();
}
}
}

Another way on Windows platform to start the default browser is ;

Runtime.getRuntime().exec
("rundll32 url.dll,FileProtocolHandler " + theUrl);

You may have difficulty to open a URL ending with .htm. All you need is to replace the last m with %6D,
like

rundll32 url.dll,FileProtocolHandler http://www.rgagnon.com/howto.htm

for

rundll32 url.dll,FileProtocolHandler http://www.rgagnon.com/howto.ht%6D

JDK1.6 has java.awt.Desktop.open(File)

See http://java.sun.com/javase/6/docs/api/java/awt/Desktop.html

JDIC provides the equivalent API for 1.4 and later.

See https://jdic.dev.java.net

try {
Desktop.browse(new URL("http://www.rgagnon.com");

}
catch (MalformedURLException e1) {
e1.printStackTrace();
}
catch (DesktopException e2) {
e2.printStackTrace();
}

See also this HowTo.

Execute a Windows Shortcut (.lnk)


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0571.html

A Shortcut is stored in a file with the extension lnk.

Execute a Windows Shortcut (.lnk) 306


Real's HowTo PDF version

// we assume that the .lnk is in the current directory


String currentDir = new File(".").getCanonicalPath();

try {
Runtime.getRuntime().exec
("cmd /c start " + currentDir + "/viewLog.lnk");
}

catch (Exception e){


JOptionPane.showMessageDialog
(null, e.getMessage(),"Oups", JOptionPane.ERROR_MESSAGE);
}

Create a file association with a Java program


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0592.html

In this example, a file with the extension .xox will be defined and associated with a java program (display
the first 10 lines of selected .xox file).

First the java program to be associated with the .xox file type.

import java.io.*;

public class Head {


static final int MAX_LINES = 10;
public static void main(String args[]) throws Exception{
String line = null;
int i = 0 ;
FileInputStream fin = new FileInputStream(args[0]);
BufferedReader myInput = new BufferedReader
(new InputStreamReader(fin));
while ( (line = myInput.readLine()) != null) {
System.out.println(line);
i++;
if (i == MAX_LINES) break;
}
BufferedReader input =
new BufferedReader(new InputStreamReader(System.in));
System.out.print("*** Press any key...");
input.readLine();
}
}

With Windows, two commands are used to define a file association, assoc and ftype. You need to execute
these commands from an account with Administrator privilege.

Create a file association with a Java program 307


Real's HowTo PDF version

To know more about these commands, type assoc /? or ftype /? .

First we define the .xox file type.

The assoc command sets up an association between a file name extension and a file type.

>assoc .xox=Xoxfile
.xox=Xoxfile

Then we specify which program is used to handle the Xoxfile type of file.

The ftype command sets up an association between a file type name, and a string to be used to execute it.

In this example, we specify the Java JVM to be used, the classpath to load the Head.class plus the
parameter (the selected .xox file).

>ftype Xoxfile=C:\Program Files\Java\jre1.5.0\bin\java -cp c:\dev\work Head %1


Xoxfile=C:\Program Files\Java\jre1.5.0\bin\java -cp c:\dev\work Head %1

Now, if you double-click on a file with .xox extension, a Dos shell is opened, the Head class is launched
with the clicked filename as a parameter and the first 10 line are displayed.

To make the file association works from a command line, you define the environment variable PATHEXT
to include the .xox extension.

>set pathext=.xox;%pathext%
PATHEXT=.XOX;.COM;.EXE;.BAT;.CMD;.VBS;.VBE;.JS;.JSE;.WSF;.WSH

then you will be able, from a Dos shell, to type only the name of .xox file and the associated program will
be launched with that file as a parameter.

See also this HowTo.

Capture the output from a VBS


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0576.html

This HowTo query the Windows Registry for a specific key. The VBS prints the result and from Java, we
capture this output.

Since we need the output, we must use the VBS interpreter for the console mode (CSCRIPT.EXE).

import java.io.BufferedReader;
import java.io.File;
import java.io.FileWriter;

Capture the output from a VBS 308


Real's HowTo PDF version

import java.io.InputStreamReader;

public class VBSUtils {


private VBSUtils() { }

public static String readWindowRegistry(String key) {


String result = "";
try {

File file = File.createTempFile("realhowto",".vbs");


file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);

String vbs = "Dim WSHShell \n"


+ "Set WSHShell = WScript.CreateObject(\"WScript.Shell\") \n"
+ "WScript.Echo _ \n"
+ "WSHShell.RegRead(\"" + key + "\") \n"
+ "Set WSHShell = Nothing \n";
fw.write(vbs);
fw.close();
Process p = Runtime.getRuntime().exec("cscript //NoLogo " + file.getPath());
BufferedReader input =
new BufferedReader
(new InputStreamReader(p.getInputStream()));
String line;
while ((line = input.readLine()) != null) {
result += line;
}
input.close();
}
catch(Exception e){
e.printStackTrace();
}
return result.trim();
}

public static void main(String[] args){


//
// DEMO
//
String result = "";
msgBox("Get the path of Acrobat reader from the registry");
result = readWindowRegistry
("HKLM\\Software\\Microsoft\\Windows\\CurrentVersion\\App Paths\\AcroRd32.exe\\");
msgBox("Acrobat Reader is located in " + result);
}

public static void msgBox(String msg) {


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, msg, "VBSUtils", javax.swing.JOptionPane.DEFAULT_OPTION);
}
}

Capture the output from a VBS 309


Real's HowTo PDF version

Get a return code from a VBS


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0575.html

You can't detect directly if Windows service is running or not in Java.

However, it's easy to do from a VBS. You execute the script from Java, wait for its completion and capture
the return code.

Obviously, this is useful only on the Windows plateform.

import java.io.File;
import java.io.FileWriter;

public class VBSUtils {


private VBSUtils() { }

public static boolean isServiceRunning(String serviceName) {


try {
File file = File.createTempFile("realhowto",".vbs");
file.deleteOnExit();
FileWriter fw = new java.io.FileWriter(file);

String vbs = "Set sh = CreateObject(\"Shell.Application\") \n"


+ "If sh.IsServiceRunning(\""+ serviceName +"\") Then \n"
+ " wscript.Quit(1) \n"
+ "End If \n"
+ "wscript.Quit(0) \n";
fw.write(vbs);
fw.close();
Process p = Runtime.getRuntime().exec("wscript " + file.getPath());
p.waitFor();
return (p.exitValue() == 1);
}
catch(Exception e){
e.printStackTrace();
}
return false;
}

public static void main(String[] args){


//
// DEMO
//
String result = "";
msgBox("Check if service 'Themes' is running (should be yes)");
result = isServiceRunning("Themes") ? "" : " NOT ";
msgBox("service 'Themes' is " + result + " running ");

Get a return code from a VBS 310


Real's HowTo PDF version

msgBox("Check if service 'foo' is running (should be no)");


result = isServiceRunning("foo") ? "" : " NOT ";
msgBox("service 'foo' is " + result + " running ");
}

public static void msgBox(String msg) {


javax.swing.JOptionPane.showConfirmDialog((java.awt.Component)
null, msg, "VBSUtils", javax.swing.JOptionPane.DEFAULT_OPTION);
}
}

Execute a CMD file stored in a JAR


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0600.html

In this example, a CMD file is stored a JAR file. The Java code extracts the file as a ressource, launch a
Windows CMD Shell and write the content to the stdin without any temporary file.

In this How-to, the CMD included is used to trigger the default Windows screen saver.

scrnsave.scr /s

import java.io.*;

public class StartScreenSaver {


public static void main(String args[]) throws IOException {
new StartScreenSaver().doit();
}

public void doit() throws IOException{


String line;
OutputStream stdin = null;
InputStream stderr = null;
InputStream stdout = null;

try {
// that our CMD file in our JAR
InputStream is =
getClass().getResource("/screensaver.cmd").openStream();
BufferedReader brCmdLine =
new BufferedReader(new InputStreamReader(is));

// launch CMD and grab stdin/stdout and stderr


Process process = Runtime.getRuntime ().exec ("cmd");
stdin = process.getOutputStream ();
stderr = process.getErrorStream ();
stdout = process.getInputStream ();

Execute a CMD file stored in a JAR 311


Real's HowTo PDF version

// "write" the CMD file into stdin


while ((line = brCmdLine.readLine()) != null) {
line += "\n";
stdin.write(line.getBytes() );
}
stdin.flush();
stdin.close();

// clean up if any output in stdout


BufferedReader brCleanUp =
new BufferedReader (new InputStreamReader (stdout));
while ((line = brCleanUp.readLine ()) != null) {
//System.out.println ("[Stdout] " + line);
}
brCleanUp.close();

// clean up if any output in stderr


brCleanUp =
new BufferedReader (new InputStreamReader (stderr));
while ((line = brCleanUp.readLine ()) != null) {
//System.out.println ("[Stderr] " + line);
}
brCleanUp.close();
}
catch (IOException e) {
e.printStackTrace();
}
finally {
stdout.close();
stderr.close();
}
}
}

Get the JAR here.

Open the default file explorer


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-open-default-os-file-explorer.html

JDK1.6
Open the default file explorer.

import java.io.File;
import java.io.IOException;
import java.awt.Desktop;

public class Test {


public static void main(String s[]) {

Open the default file explorer 312


Real's HowTo PDF version

Desktop desktop = null;


// on Windows, retrieve the path of the "Program Files" folder
File file = new File(System.getenv("programfiles"));

try {
if (Desktop.isDesktopSupported()) {
desktop = Desktop.getDesktop();
desktop.open(file);
}
else {
System.out.println("desktop is not supported");
}
catch (IOException e){ }
}
}

Read the content of a file


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0052.html

From a Java application

This following example is for an application.

import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.InputStreamReader;

public class Cat {


public static void main (String args[]) throws Exception {
String line;
FileInputStream fin = null;
BufferedReader br = null;
InputStreamReader isr = null;

try {
fin = new FileInputStream("D:/temp/howto.txt");
isr = new InputStreamReader(fin);
br = new BufferedReader(isr);
while ((line = br.readLine()) != null) {
System.out.println(line);
}
}
finally {
if (br != null) br.close();
if (isr != null) isr.close();
if (fin != null) fin.close();
}
}

Read the content of a file 313


Real's HowTo PDF version

The following method read a data file and return the content as a String. We use a StringBuilder to optimize
string concatenation operations.

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;

public class Cat {


public static final String EOL = System.getProperty("line.separator");

private static String readFile(String filename) throws IOException {


BufferedReader br = null;
FileReader fr = null;

try {
fr = new FileReader(filename);
br = new BufferedReader(fr);
String nextLine = "";
StringBuilder sb = new StringBuilder();
while ((nextLine = br.readLine()) != null) {
sb.append(nextLine); // note: BufferedReader strips the EOL character
// so we add a new one!
sb.append(EOL);
}
return sb.toString();
}
finally {
if (br != null) br.close();
if (fr != null) fr.close();
}
}

public static void main (String args[]) throws Exception {


System.out.println(readFile("d:/temp/howto.txt"));
}
}

JDK1.5 provides the java.util.Scanner class which can be used to quickly read a file.

The delimeter "\Z" represents the end-of-file marker.

import java.io.File;
import java.io.FileNotFoundException;
import java.util.Scanner;

public class QuickFileRead {


public static void main(String[] args) throws FileNotFoundException {
Scanner scanner =
new Scanner(new File("c:/temp/text.txt")).useDelimiter("\\Z");
String contents = scanner.next();
System.out.println(contents);

Read the content of a file 314


Real's HowTo PDF version

scanner.close();
}
}

JDK7+ provides, with the NIO package, a new way to get all the content of file quickly. You don't need to
close anything because readAllLines() is taking care of that.

import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.List;

public class Cat {


public static void main (String args[]) throws Exception {
Path path = Paths.get( "d:/temp/howto.txt" );
List <String> lines = Files.readAllLines(path, StandardCharsets.UTF_8);
for (String element : lines) {
System.out.println(element);
}
}
}

See this HowTo to read a file stored in a JAR.

Read a text file from a Jar


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0077.html

import java.io.*;
import java.util.*;

public class FileUtils{

public static List<String> readTextFromJar(String s) {


InputStream is = null;
BufferedReader br = null;
String line;
ArrayList<String> list = new ArrayList<String>();

try {
is = FileUtils.class.getResourceAsStream(s);
br = new BufferedReader(new InputStreamReader(is));
while (null != (line = br.readLine())) {
list.add(line);
}
}
catch (Exception e) {

Read a text file from a Jar 315


Real's HowTo PDF version

e.printStackTrace();
}
finally {
try {
if (br != null) br.close();
if (is != null) is.close();
}
catch (IOException e) {
e.printStackTrace();
}
}
return list;
}

public static void main(String args[]) throws IOException{


List<String> list = FileUtils.readTextFromJar("/datafile1.txt");
Iterator<String> it = list.iterator();
while(it.hasNext()) {
System.out.println(it.next());
}

list = FileUtils.readTextFromJar("/test/datafile2.txt");
it = list.iterator();
while(it.hasNext()) {
System.out.println(it.next());
}
}
}

Create 2 datafiles.

datafile1.txt in the same directory as FileUtils.class (in the root) and datafile2.txt in a subdirectory called
test

[datafile1.txt]

datafile1 line 1
datafile1 line 2
datafile1 line 3
datafile1 line 4
datafile1 line 5

[/test/datafile2.txt]

datafile2 line 1
datafile2 line 2
datafile2 line 3
datafile2 line 4
datafile2 line 5

Create the jar with

Read a text file from a Jar 316


Real's HowTo PDF version

>"C:\Program Files\Java\jdk1.5.0\bin\jar" -cf MyJar.jar


FileUtils.class datafile.txt test/datafile.txt

Try it :

C> java -cp MyJar.jar FileUtils

The output should be like :

datafile1 line 1
datafile1 line 2
datafile1 line 3
datafile1 line 4
datafile1 line 5
datafile2 line 1
datafile2 line 2
datafile2 line 3
datafile2 line 4
datafile2 line 5

Get the JAR here

With an Applet, it's the same technique

import java.applet.*;
import java.io.*;

public class ReadFromJar extends Applet{

public void init(){


readTextFromJar("datafile1.txt");
readTextFromJar("test/datafile2.txt");
}

public void readTextFromJar(String s) {


String thisLine;
try {
InputStream is = getClass().getResourceAsStream(s);
BufferedReader br = new BufferedReader
(new InputStreamReader(is));
while ((thisLine = br.readLine()) != null) {
System.out.println(thisLine);
}
}
catch (Exception e) {
e.printStackTrace();
}
}
}

Create the JAR

Read a text file from a Jar 317


Real's HowTo PDF version

>"C:\Program Files\Java\jdk1.5.0\bin\jar" -cf


MyJarApplet.jar ReadFromJar.class datafile1.txt test/datafile2.txt

The html

<HTML><HEAD></HEAD><BODY>
<APPLET CODE=ReadFromJar.class width=1 height=1 archive=MyJarApplet.jar>
</APPLET>
See java console for output</BODY></HTML>

Try it here

Read a text file from the internet


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-read-a-file-from-the-internet.html

import java.io.IOException;
import java.net.URL;
import java.util.Scanner;

public class NetUtils {

private NetUtils() {}

public static String getTextContent(URL url) throws IOException {


Scanner s = new Scanner(url.openStream()).useDelimiter("\\Z");;
String content = s.next();
return content;
}

public static void main(String[] args) throws IOException {


URL url = new URL("http://www.rgagnon.com/varia/copyrightnotice.txt");
System.out.println(NetUtils.getTextContent(url));
}
}

Extract a file from a Jar


Current version of this HowTo :
http://www.rgagnon.com/javadetails/../javadetails/java-0429.html

The following snippet extract a file (mydb.mdb) from a jar.

import java.io.*;
import java.util.jar.*;

Read a text file from the internet 318


Real's HowTo PDF version

import java.util.zip.*;

public class ExtractFromJAR {

public void extractMyMDBromJAR(String dest){


try {
String home = getClass().getProtectionDomain().
getCodeSource().getLocation().toString().
substring(6);
JarFile jar = new JarFile(home);
ZipEntry entry = jar.getEntry("mydb.mdb");
File efile = new File(dest, entry.getName());

InputStream in =
new BufferedInputStream(jar.getInputStream(entry));
OutputStream out =
new BufferedOutputStream(new FileOutputStream(efile));
byte[] buffer = new byte[2048];
for (;;) {
int nBytes = in.read(buffer)