package de.macarony;
import java.awt.Color;
import java.awt.Cursor;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.util.Calendar;
import java.util.Properties;
import javax.swing.JPanel;
import javax.swing.JWindow;
import javax.swing.Timer;
import javax.swing.event.MouseInputListener;
/**
* class BinClock shows a java swing binary clock
* @author marco@macarony.de
*/
class BinClock extends JWindow implements Runnable,MouseInputListener,ActionListener{
private static final long serialVersionUID = 8992498180259574922L;
/**
* BINCLOCK_VERSION contains the build version (date)
*/
private static final String BINCLOCK_VERSION="20061212";
/**
* REFRESH_TIMER is the timer setting for repainting the clock (DEFAULT - 250 ms);
*/
private static final int REFRESH_TIMER=250;
/**
* RED is a Byte constant for the color
*/
private static final byte RED=1;
/**
* GREEN is a Byte constant for the color
*/
private static final byte GREEN=2;
/**
* BLUE is a Byte constant for the color
*/
private static final byte BLUE=3;
/**
* DEFAULT_PROP_FILE=System.getProperty("user.home")+System.getProperty("file.separator")+".BinClock.properties"
*/
private static final String DEFAULT_PROP_FILE=System.getProperty("user.home")+System.getProperty("file.separator")+".BinClock.properties";
/**
* DEFAULT_COLOR=Color.WHITE
*/
private static final Color DEFAULT_COLOR=Color.WHITE;
/**
* DEFAULT_BGCOLOR=new Color(255,127,63)
*/
private static final Color DEFAULT_BGCOLOR=new Color(255,127,63);
/**
* DEFAULT_HOUR24=true => 24 hour mode is enabled by default
*/
private static final boolean DEFAULT_HOUR24=true;
/**
* DEFAULT_ALWAYSONTOP=true => BinClock is always on top by default
*/
private static final boolean DEFAULT_ALWAYSONTOP=true;
/**
* DEFAULT_RECTANGLE=false => BinClock uses arcs by default
*/
private static final boolean DEFAULT_RECTANGLE=false;
/**
* DEFAULT_SIZE=2 => BinClock has size "2" by default - values in range 0-4
*/
private static final int DEFAULT_SIZE=2;
/**
* MODE_NORMAL is a Byte constant for the mode
*/
private static final byte MODE_NORMAL=0;
/**
* MODE_CONFIG is a Byte constant for the mode
*/
private static final byte MODE_CONFIG=1;
/**
* MODE_COMPACT is a Byte constant for the mode
*/
private static final byte MODE_COMPACT=-1;
/**
* clock_panel is the JPanel to draw the BinClock (contentPane)
*/
private JPanel clock_panel;
/**
* prop_file will contain the String path to .properties file (DEFAULT or user option)
*/
private String prop_file;
/**
* prop is used to store the Properties set from .properties file
*/
private Properties prop;
/**
* hour24 is a boolean for 24 hour mode
*/
private boolean hour24;
/**
* rgb will contain the color, which is to change (RED,GREEN,BLUE) - config mode
*/
private byte rgb;
/**
* color is the Color value for foreground
*/
private Color color;
/**
* bgcolor is the Color value for background
*/
private Color bgcolor;
/**
* store_size is the int size value that is stored in .properties file - values in range 0-4
*/
private int store_size;
/**
* size is the int size, which is used by BinClock to work with
* size=((int)Math.pow(2,store_size))*10;
*/
private int size;
/**
* gap is the int gap between the arcs/rectangles
* gap=size/10;
*/
private int gap;
/**
* rectangle is a boolean for rectangle if false then arc mode is used
*/
private boolean rectangle;
/**
* invert is used to show the clock from bottom to top
* byte value is used because the paint position is calculated by invert-position
*/
private byte invert;
/**
* alwaysontop is a boolean that brings the clock on top of each other window
*/
private boolean alwaysontop;
/**
* posdiff will contain the position difference between the BinClock origin(0,0) and the mouse position on moving event
*/
private Point posdiff;
/**
* mode has to be one of the three states: MODE_NORMAL,MODE_CONFIG or MODE_COMPACT
*/
private byte mode;
/**
* change_color is used to indicate, if the choosen color should be increased or decreased
* int value of x-axis that is greater(inc) or lower(dec) than size/2
*/
private int change_color;
/**
* color_timer is the Timer to change the specified color while mouse button is pressed
*/
private Timer color_timer;
/**
* REFRESH_COLOR_TIMER is the timer setting color change while mousePressed (DEFAULT - 10 ms);
*/
private static final int REFRESH_COLOR_TIMER=10;
/**
* BinClock standard constructor is called if no command line arguments are passed
* it uses the standard .properties file and initializes the clock
*/
public BinClock(){
super();
this.prop_file=BinClock.DEFAULT_PROP_FILE;
this.getConfig();
this.init();
}
/**
* BinClock(String[] args) constructor is called if command line arguments are passed
* it parses all arguments and initializes the clock this way
* command line arguments are prior .properties file options
* @param args String[] the command line arguments are passed to this constructor
*/
public BinClock(String[] args){
super();
this.prop_file=BinClock.DEFAULT_PROP_FILE;
//search for another .properties file in args
for(int i=0;i overwrite all - command line has first priority
for(int i=0;i4){
this.store_size=4;
}else if(this.store_size<0){
this.store_size=0;
}
this.size=((int)Math.pow(2,this.store_size))*10;
this.gap=this.size/10;
if(newpos){
this.setLocation((int)Toolkit.getDefaultToolkit().getScreenSize().getWidth()-(5+this.size),this.getY());
}
}catch(Exception e){
}
}else if(key.equals("xpos")){
try{
int xpos=Integer.parseInt(args[i].substring(args[i].indexOf("=")+1));
this.setLocation(xpos,this.getY());
}catch(Exception e){
}
}else if(key.equals("ypos")){
try{
int ypos=Integer.parseInt(args[i].substring(args[i].indexOf("=")+1));
this.setLocation(this.getX(),ypos);
}catch(Exception e){
}
}else if(key.equals("alwaysontop")){
this.alwaysontop=this.isVar(args[i].substring(args[i].indexOf("=")+1));
}else if(key.equals("rectangle")){
this.rectangle=this.isVar(args[i].substring(args[i].indexOf("=")+1));
}else if(key.equals("invert")){
if(this.isVar(args[i].substring(args[i].indexOf("=")+1))){
this.invert=0;
}else{
this.invert=5;
}
}else if(key.equals("compact")){
if(this.isVar(args[i].substring(args[i].indexOf("=")+1))){
this.mode=BinClock.MODE_COMPACT;
}else{
this.mode=BinClock.MODE_NORMAL;
}
}
}else if(args[i].substring(0,2).equals("-c")){
this.mode=BinClock.MODE_COMPACT;
}else if(args[i].equals("-alwaysontop")){
this.alwaysontop=true;
}else if(args[i].equals("-hour24")){
this.hour24=true;
}else if(args[i].equals("-invert")){
this.invert=0;
}else if(args[i].equals("-rectangle")){
this.rectangle=true;
//ask for version? -> show version and exit
}else if(args[i].substring(0,2).equals("-v")){
System.out.println(BinClock.class.getName()+" - version: "+BinClock.BINCLOCK_VERSION);
System.exit(0);
//ask for help? -> show help and exit
}else if(args[i].substring(0,2).equals("-h")){
System.out.println("Usage: "+BinClock.class.getName()+" [option]");
System.out.println("========================================");
System.out.println("-alwaysontop[=TF-Value]\t(="+BinClock.DEFAULT_ALWAYSONTOP+") window is always on top");
System.out.println("-bgcolor=rrggbb\t\t(="+Integer.toHexString(BinClock.DEFAULT_BGCOLOR.getRGB()).substring(2,8)+") background color value as 2-digit hex");
System.out.println("-color=rrggbb\t\t(="+Integer.toHexString(BinClock.DEFAULT_COLOR.getRGB()).substring(2,8)+") foreground color value as 2-digit hex");
System.out.println("-c[ompact[=TF-Value]]\t(=false) start in compact mode");
System.out.println("-config=filename\t(="+BinClock.DEFAULT_PROP_FILE+") config file name");
System.out.println("-h[elp]\t\t\tprint this message");
System.out.println("-hour24[=TF-Value]\t(="+BinClock.DEFAULT_HOUR24+") 24 hour clock or 12 hour clock");
System.out.println("-invert[=TF-Value]\t(=false): 32,16,8,4,2,1 invert: 1,2,4,8,16,32");
System.out.println("-rectangle[=TF-Value]\t(="+BinClock.DEFAULT_RECTANGLE+") rectangle(=true) mode or arc(=false)");
System.out.println("-size=n\t\t\t(="+Integer.toString(BinClock.DEFAULT_SIZE)+") size of the clock value: 1-5");
System.out.println("-v[ersion]\t\tprint version (="+BinClock.BINCLOCK_VERSION+")");
System.out.println("\nTF-Value\t\t(1|0|on|off|true|false|yes|no) - no \"=TF-value\" == true");
System.exit(0);
}
}
this.init();
}
/**
* actionPerformed(ActionEvent e) is used for Timer event on color change
* @param e ActionEvent only Timer is supported as event source
*/
private boolean actionPerformed_bg;
public void actionPerformed(ActionEvent e){
if(e.getSource().getClass().equals(Timer.class)){
this.actionPerformed_bg=false;
if(this.rgb<0){
this.actionPerformed_bg=true;
}
if(Math.abs(this.rgb)==BinClock.BLUE){
if(this.change_color>this.size/2){
if(this.actionPerformed_bg){
if(this.bgcolor.getBlue()<255){
this.bgcolor=new Color(this.bgcolor.getRed(),this.bgcolor.getGreen(),this.bgcolor.getBlue()+1);
}
}else{
if(this.color.getBlue()<255){
this.color=new Color(this.color.getRed(),this.color.getGreen(),this.color.getBlue()+1);
}
}
}else{
if(this.actionPerformed_bg){
if(this.bgcolor.getBlue()>0){
this.bgcolor=new Color(this.bgcolor.getRed(),this.bgcolor.getGreen(),this.bgcolor.getBlue()-1);
}
}else{
if(this.color.getBlue()>0){
this.color=new Color(this.color.getRed(),this.color.getGreen(),this.color.getBlue()-1);
}
}
}
}else if(Math.abs(this.rgb)==BinClock.GREEN){
if(this.change_color>this.size/2){
if(this.actionPerformed_bg){
if(this.bgcolor.getGreen()<255){
this.bgcolor=new Color(this.bgcolor.getRed(),this.bgcolor.getGreen()+1,this.bgcolor.getBlue());
}
}else{
if(this.color.getGreen()<255){
this.color=new Color(this.color.getRed(),this.color.getGreen()+1,this.color.getBlue());
}
}
}else{
if(this.actionPerformed_bg){
if(this.bgcolor.getGreen()>0){
this.bgcolor=new Color(this.bgcolor.getRed(),this.bgcolor.getGreen()-1,this.bgcolor.getBlue());
}
}else{
if(this.color.getGreen()>0){
this.color=new Color(this.color.getRed(),this.color.getGreen()-1,this.color.getBlue());
}
}
}
}else if(Math.abs(this.rgb)==BinClock.RED){
if(this.change_color>this.size/2){
if(this.actionPerformed_bg){
if(this.bgcolor.getRed()<255){
this.bgcolor=new Color(this.bgcolor.getRed()+1,this.bgcolor.getGreen(),this.bgcolor.getBlue());
}
}else{
if(this.color.getRed()<255){
this.color=new Color(this.color.getRed()+1,this.color.getGreen(),this.color.getBlue());
}
}
}else{
if(this.actionPerformed_bg){
if(this.bgcolor.getRed()>0){
this.bgcolor=new Color(this.bgcolor.getRed()-1,this.bgcolor.getGreen(),this.bgcolor.getBlue());
}
}else{
if(this.color.getRed()>0){
this.color=new Color(this.color.getRed()-1,this.color.getGreen(),this.color.getBlue());
}
}
}
}
this.clock_panel.setBackground(BinClock.this.bgcolor);
}
}
/**
* getConfig() reads the Properties from .properties file
* if no properties where found (file does not exists or property not defined) configuration is done by DEFAULT_value
*/
private void getConfig(){
this.mode=BinClock.MODE_NORMAL;
this.prop=new Properties();
this.hour24=BinClock.DEFAULT_HOUR24;
this.rgb=0;
this.color=BinClock.DEFAULT_COLOR;
this.bgcolor=BinClock.DEFAULT_BGCOLOR;
this.store_size=BinClock.DEFAULT_SIZE;
this.posdiff=null;
this.alwaysontop=BinClock.DEFAULT_ALWAYSONTOP;
this.rectangle=BinClock.DEFAULT_RECTANGLE;
this.invert=5;
this.change_color=0;
this.color_timer=new Timer(BinClock.REFRESH_COLOR_TIMER,this);
int xpos=Integer.MIN_VALUE;
int ypos=0;
try{
if(new File(this.prop_file).exists()){
this.prop.load(new FileInputStream(this.prop_file));
}else if(this.getClass().getResourceAsStream("/"+this.prop_file)!=null){
this.prop.load(this.getClass().getResourceAsStream("/"+this.prop_file));
}else{
this.prop.setProperty("NO_PROPERTIES","");
}
//do only if .properties file is found
if(!this.prop.contains("NO_PROPERTIES")){
if(this.prop.getProperty("hour24")!=null){
this.hour24=this.isVar(this.prop.getProperty("hour24"));
}
try{
this.color=new Color(Integer.parseInt(this.prop.getProperty("color"),16));
}catch(Exception ex){
}
try{
this.bgcolor=new Color(Integer.parseInt(this.prop.getProperty("bgcolor"),16));
}catch(Exception ex){
}
try{
this.store_size=Integer.parseInt(this.prop.getProperty("size"));
}catch(Exception ex){
}
try{
xpos=Integer.parseInt(this.prop.getProperty("xpos"));
}catch(Exception ex){
}
try{
ypos=Integer.parseInt(this.prop.getProperty("ypos"));
}catch(Exception ex){
}
if(this.prop.getProperty("alwaysontop")!=null){
this.alwaysontop=this.isVar(this.prop.getProperty("alwaysontop"));
}
if(this.prop.getProperty("rectangle")!=null){
this.rectangle=this.isVar(this.prop.getProperty("rectangle"));
}
if(this.prop.getProperty("invert")!=null){
if(this.isVar(this.prop.getProperty("invert"))){
this.invert=0;
}else{
this.invert=5;
}
}
}
}catch(Exception ex){
}
//calculate internal size and gap values from store_size
if(this.store_size>4){
this.store_size=4;
}else if(this.store_size<0){
this.store_size=0;
}
this.size=((int)Math.pow(2,store_size))*10;
this.gap=this.size/10;
//create new x postion if none is given (right corner)
if(xpos==Integer.MIN_VALUE){
xpos=(int)Toolkit.getDefaultToolkit().getScreenSize().getWidth()-(5+this.size);
}
this.setLocation(xpos,ypos);
}
/**
* inRange(MouseEvent e,int line,boolean is_rectangle) checks if the mouse position is in the expected range
* @param e MouseEvent need the position of the mouse event
* @param line int is the line in which the event should be negativ value is the inner area
* @param is_rectangle boolean is it an rectangle or arc area
* @return if in range return true else range is missed - return false
*/
private boolean inRange(MouseEvent e,int line,boolean is_rectangle){
//in MODE_COMPACT is just one event accepted (System.exit(0)) so all clicks are good
if(this.mode==BinClock.MODE_COMPACT){
return(true);
}else if(is_rectangle){
if(line<0){
line=-(line+1);
if(((e.getX()>(2+(this.size/4)))&&(e.getX()<(2+((this.size/4)*3))))
&&((e.getY()>(2+(line*this.size)+(line*this.gap)+(this.size/4)))
&&(e.getY()<(2+(line*this.size)+(line*this.gap)+((this.size/4)*3))))){
return(true);
}
}else{
line=line-1;
if(((e.getX()>2)&&(e.getX()<(2+this.size)))
&&((e.getY()>(2+(line*this.size)+(line*this.gap)))
&&(e.getY()<(2+((1+line)*this.size)+(line*this.gap))))){
return(true);
}
}
}else{
if(line<0){
line=-(line+1);
if(e.getPoint().distance(2+(this.size/2),2+(this.size/2)+(line*this.size)+(line*this.gap))
* no further params or return just show it
*/
private void init(){
new Thread(this).start();
this.setContentPane(this.paintClockPanel());
this.addMouseListener(this);
this.addMouseMotionListener(this);
this.pack();
this.setVisible(true);
}
/**
* isVar(String var) checks if a given value is accepted as boolean true
* config syntax used by BinClock for writing .properties file is "1|0"
* @param var String accepted as true are: "true|yes|on|1" - all incasesensitive
* @return boolean true if the given value is accepted as true value
*/
private boolean isVar(String var){
String[] var4true=new String[4];
var4true[0]="true";
var4true[1]="yes";
var4true[2]="on";
var4true[3]="1";
for(int i=0;i
* @param e MouseEvent need the clickCount
*/
private boolean mouseClicked_reset;
public void mouseClicked(MouseEvent e){
if(e.getClickCount()>=2){
if(this.inRange(e,-1,this.rectangle)){
System.exit(0);
}else if(this.inRange(e,1,this.rectangle)){
if(this.mode==BinClock.MODE_CONFIG){
this.store();
this.mode=BinClock.MODE_NORMAL;
}else{
this.mode=BinClock.MODE_CONFIG;
}
}
}else if(this.mode==BinClock.MODE_CONFIG){
this.mouseClicked_reset=false;
if(this.inRange(e,-2,this.rectangle)){
if(this.hour24){
this.hour24=false;
}else{
this.hour24=true;
}
}else if(this.inRange(e,2,this.rectangle)){
if(this.alwaysontop){
this.alwaysontop=false;
this.toBack();
}else{
this.alwaysontop=true;
this.toFront();
}
}else if((this.inRange(e,3,!this.rectangle))&&((e.getX()-2)<(this.size/2))){
if(this.rectangle){
this.rectangle=false;
}else{
this.rectangle=true;
}
}else if(this.inRange(e,-3,this.rectangle)){
if(this.store_size>0){
this.store_size--;
this.mouseClicked_reset=true;
}
}else if(this.inRange(e,3,this.rectangle)){
if(this.store_size<5){
this.store_size++;
this.mouseClicked_reset=true;
}
}
if(this.mouseClicked_reset){
this.setVisible(false);
this.size=((int)Math.pow(2,store_size))*10;
this.gap=this.size/10;
this.setContentPane(this.paintClockPanel());
this.pack();
this.setVisible(true);
}
}
}
/**
* mousePressed(MouseEvent e) used for start of color change and moving
* @param e MouseEvent need the position of the mouse event
*/
public void mousePressed(MouseEvent e){
if(this.inRange(e,1,this.rectangle)){
this.posdiff=new Point(e.getX(),e.getY());
this.setCursor(new Cursor(Cursor.MOVE_CURSOR));
}
if(this.mode==BinClock.MODE_CONFIG){
if(this.inRange(e,1,this.rectangle)){
this.posdiff=new Point(e.getX(),e.getY());
this.setCursor(new Cursor(Cursor.MOVE_CURSOR));
}else if(this.inRange(e,-4,this.rectangle)){
this.rgb=BinClock.RED;
}else if(this.inRange(e,4,this.rectangle)){
this.rgb=-BinClock.RED;
}else if(this.inRange(e,-5,this.rectangle)){
this.rgb=BinClock.GREEN;
}else if(this.inRange(e,5,this.rectangle)){
this.rgb=-BinClock.GREEN;
}else if(this.inRange(e,-6,this.rectangle)){
this.rgb=BinClock.BLUE;
}else if(this.inRange(e,6,this.rectangle)){
this.rgb=-BinClock.BLUE;
}
if(this.rgb!=0){
this.change_color=e.getX()-2;
this.color_timer.start();
}
}
}
/**
* mouseReleased(MouseEvent e) used for end of color change and moving
* @param e MouseEvent not used
*/
public void mouseReleased(MouseEvent e){
if(this.posdiff!=null){
this.posdiff=null;
this.setCursor(new Cursor(Cursor.DEFAULT_CURSOR));
}
if((this.mode==BinClock.MODE_CONFIG)&&(this.rgb!=0)){
this.rgb=0;
this.change_color=0;
this.color_timer.stop();
}
}
/**
* mouseEntered(MouseEvent e) bring window to front
* @param e MouseEvent not used
*/
public void mouseEntered(MouseEvent e){
this.toFront();
}
/**
* mouseExited(MouseEvent e) send window to back if not always on top
* @param e MouseEvent not used
*/
public void mouseExited(MouseEvent e){
if(!this.alwaysontop){
this.toBack();
}
}
/**
* mouseDragged(MouseEvent e) used for moving and stopping color change (if mouse outside area)
* @param e MouseEvent need the position of the mouse event
*/
public void mouseDragged(MouseEvent e){
if(this.posdiff!=null){
this.setLocation(this.getX()-this.posdiff.x+e.getX(),this.getY()-this.posdiff.y+e.getY());
}
//leave color change area without release of mouse button
if((this.mode==BinClock.MODE_CONFIG)&&(!this.inRange(e,((this.rgb+3)*-1),this.rectangle))){
this.rgb=0;
this.change_color=0;
this.color_timer.stop();
}
}
/**
* mouseMoved(MouseEvent e) used for changing cursor in normal mode
* exit range: CROSSHAIR_CURSOR
* config range: HAND_CURSOR
* @param e MouseEvent need the position of the mouse event
*/
public void mouseMoved(MouseEvent e){
if((this.mode==BinClock.MODE_NORMAL)&&(this.posdiff==null)){
if(this.inRange(e,-1,this.rectangle)){
this.setCursor(new Cursor(Cursor.CROSSHAIR_CURSOR));
}else if(this.inRange(e,1,this.rectangle)){
this.setCursor(new Cursor(Cursor.HAND_CURSOR));
}else{
this.setCursor(new Cursor(Cursor.DEFAULT_CURSOR));
}
}
}
/**
* paintClockPanel() work is done here.. for each Timer call the binary clock is repainted
*/
private JPanel paintClockPanel(){
this.clock_panel=new JPanel(true){
private static final long serialVersionUID = 320290428820213047L;
private Calendar now;
private int second;
private int minute;
private int hour;
private byte pos;
private boolean fill;
private int sizediff;
public void paintComponent(Graphics g){
super.paintComponent(g);
this.now=Calendar.getInstance();
this.second=this.now.get(Calendar.SECOND);
this.minute=this.now.get(Calendar.MINUTE);
if(BinClock.this.hour24){
this.hour=this.now.get(Calendar.HOUR_OF_DAY);
}else{
this.hour=this.now.get(Calendar.HOUR);
}
if(BinClock.this.mode==BinClock.MODE_COMPACT){
for(this.pos=5;this.pos>=0;this.pos--){
if((this.second-Math.pow(2,this.pos))>=0){
this.second=this.second-((int)Math.pow(2,this.pos));
g.setColor(BinClock.this.color);
}else{
g.setColor(BinClock.this.bgcolor);
}
g.fillArc(2,2,BinClock.this.size,BinClock.this.size,((-60*this.pos)+90),-60);
if((this.minute-Math.pow(2,this.pos))>=0){
this.minute=this.minute-((int)Math.pow(2,this.pos));
g.setColor(BinClock.this.color);
}else{
g.setColor(BinClock.this.bgcolor);
}
g.fillArc(2+(BinClock.this.gap/4),2+(BinClock.this.gap/4),
BinClock.this.size-(BinClock.this.gap/2),
BinClock.this.size-(BinClock.this.gap/2),((-60*this.pos)+90),-60);
if((this.hour-Math.pow(2,this.pos))>=0){
this.hour=this.hour-((int)Math.pow(2,this.pos));
g.setColor(BinClock.this.color);
}else{
g.setColor(BinClock.this.bgcolor);
}
g.fillArc(2+(BinClock.this.size/4),2+(BinClock.this.size/4),
BinClock.this.size/2,BinClock.this.size/2,((-60*this.pos)+90),-60);
}
}else{
for(this.pos=5;this.pos>=0;this.pos--){
if(BinClock.this.mode==BinClock.MODE_CONFIG){
this.sizediff=0;
switch(this.pos){
case 5:
g.setColor(BinClock.this.color);
break;
case 4:
if(BinClock.this.alwaysontop){
g.setColor(Color.BLUE);
}else{
g.setColor(BinClock.this.bgcolor);
}
break;
case 3:
this.sizediff=(((int)Math.pow(2,(BinClock.this.store_size+1)))*10)-BinClock.this.size;
g.setColor(BinClock.this.color);
break;
case 2:
g.setColor(Color.RED);
break;
case 1:
g.setColor(Color.GREEN);
break;
case 0:
g.setColor(Color.BLUE);
break;
}
if(BinClock.this.rectangle){
if(this.pos==3){
g.fillRect(2+(BinClock.this.size/2),
(2+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/2)),
((BinClock.this.size/2)+this.sizediff),
(BinClock.this.size+this.sizediff));
}else{
g.fillRect((2-(this.sizediff/2)),
(2+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/2)),
(BinClock.this.size+this.sizediff),
(BinClock.this.size+this.sizediff));
}
}else{
if(this.pos==3){
g.fillArc((2-(this.sizediff/2)),
(2+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/2)),
(BinClock.this.size+this.sizediff),
(BinClock.this.size+this.sizediff),270,180);
}else{
g.fillArc((2-(this.sizediff/2)),
(2+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/2)),
(BinClock.this.size+this.sizediff),
(BinClock.this.size+this.sizediff),0,360);
}
}
this.fill=true;
switch(this.pos){
case 5:
g.setColor(BinClock.this.bgcolor);
break;
case 4:
g.setColor(BinClock.this.bgcolor);
if(BinClock.this.rectangle){
g.fillRect((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),
((BinClock.this.size/2)+(this.sizediff/4)));
}else{
g.fillArc((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),
((BinClock.this.size/2)+(this.sizediff/4)),0,360);
}
g.setColor(BinClock.this.color);
if(!BinClock.this.hour24){
this.fill=false;
}
break;
case 3:
g.setColor(BinClock.this.bgcolor);
if(BinClock.this.rectangle){
g.fillRect((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),
((BinClock.this.size/2)+(this.sizediff/4)));
}else{
g.fillArc((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),
((BinClock.this.size/2)+(this.sizediff/4)),0,360);
}
this.sizediff=(((int)Math.pow(2,(BinClock.this.store_size-1)))*10)-BinClock.this.size;
g.setColor(BinClock.this.color);
break;
case 2:
g.setColor(BinClock.this.bgcolor);
g.drawLine(2+(BinClock.this.size/2),
2+(((5-this.pos)*BinClock.this.size)+(5-this.pos)*BinClock.this.gap),
2+(BinClock.this.size/2),2+(((5-this.pos+1)*BinClock.this.size)+(5-this.pos)*BinClock.this.gap));
this.fill=false;
break;
case 1:
g.setColor(BinClock.this.bgcolor);
g.drawLine(2+(BinClock.this.size/2),
2+(((5-this.pos)*BinClock.this.size)+(5-this.pos)*BinClock.this.gap),
2+(BinClock.this.size/2),2+(((5-this.pos+1)*BinClock.this.size)+(5-this.pos)*BinClock.this.gap));
this.fill=false;
break;
case 0:
g.setColor(BinClock.this.bgcolor);
g.drawLine(2+(BinClock.this.size/2),
2+(((5-this.pos)*BinClock.this.size)+(5-this.pos)*BinClock.this.gap),
2+(BinClock.this.size/2),2+(((5-this.pos+1)*BinClock.this.size)+(5-this.pos)*BinClock.this.gap));
this.fill=false;
break;
}
if(this.fill){
if(BinClock.this.rectangle){
g.fillRect((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),((BinClock.this.size/2)+(this.sizediff/4)));
}else{
g.fillArc((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),((BinClock.this.size/2)+(this.sizediff/4)),0,360);
}
}else{
if(BinClock.this.rectangle){
g.drawRect((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),((BinClock.this.size/2)+(this.sizediff/4)));
}else{
g.drawArc((2+(BinClock.this.size/4)-(this.sizediff/8)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)-(this.sizediff/8)),
((BinClock.this.size/2)+(this.sizediff/4)),((BinClock.this.size/2)+(this.sizediff/4)),0,360);
}
}
if(this.pos==3){
if(rectangle){
g.fillArc(2,(2+(2*BinClock.this.size)+(2*BinClock.this.gap)),
2+(BinClock.this.size),BinClock.this.size,90,180);
g.drawRect((2+(BinClock.this.size/4)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)),
(BinClock.this.size/2),(BinClock.this.size/2));
}else{
g.fillRect(2,(2+(2*BinClock.this.size)+(2*BinClock.this.gap)),2+(BinClock.this.size/2),BinClock.this.size);
g.drawArc((2+(BinClock.this.size/4)),
(2+(BinClock.this.size/4)+((5-this.pos)*BinClock.this.size)+((5-this.pos)*BinClock.this.gap)),
(BinClock.this.size/2),(BinClock.this.size/2),270,180);
}
}
}else{
if((this.minute-Math.pow(2,this.pos))>=0){
this.minute=this.minute-((int)Math.pow(2,this.pos));
g.setColor(BinClock.this.color);
if(BinClock.this.rectangle){
g.fillRect(2,(2+(Math.abs(BinClock.this.invert-this.pos)*BinClock.this.size)+(Math.abs(BinClock.this.invert-this.pos)*BinClock.this.gap)),
(BinClock.this.size/8)*7,BinClock.this.size);
}else{
g.fillArc(2,(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size,BinClock.this.size,45,270);
}
}else{
g.setColor(BinClock.this.color);
if(BinClock.this.rectangle){
g.drawRect(2,(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
(BinClock.this.size/8)*7,BinClock.this.size);
}else{
g.drawArc(2,(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size,BinClock.this.size,45,270);
}
}
if((this.hour-Math.pow(2,this.pos))>=0){
this.hour=this.hour-((int)Math.pow(2,this.pos));
g.setColor(BinClock.this.color);
if(BinClock.this.rectangle){
g.fillRect((2+(BinClock.this.size/4)),
(2+(BinClock.this.size/4)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
(BinClock.this.size/2),(BinClock.this.size/2));
}else{
g.fillArc((2+(BinClock.this.size/4)),
(2+(BinClock.this.size/4)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
(BinClock.this.size/2),(BinClock.this.size/2),0,360);
}
}else{
g.setColor(BinClock.this.bgcolor);
if(BinClock.this.rectangle){
g.fillRect((2+(BinClock.this.size/4)),
(2+(BinClock.this.size/4)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
(BinClock.this.size/2),(BinClock.this.size/2));
}else{
g.fillArc((2+(BinClock.this.size/4)),
(2+(BinClock.this.size/4)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
(BinClock.this.size/2),(BinClock.this.size/2),0,360);
}
}
if((this.second-Math.pow(2,this.pos))>=0){
this.second=this.second-((int)Math.pow(2,this.pos));
g.setColor(BinClock.this.color);
if(BinClock.this.rectangle){
g.fillRect(2+((BinClock.this.size/8)*7),
(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size/8,BinClock.this.size);
}else{
g.fillArc(2,(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size,BinClock.this.size,315,90);
}
}else{
if(BinClock.this.rectangle){
g.setColor(BinClock.this.color);
g.drawRect(2+((BinClock.this.size/8)*7),
(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size/8,BinClock.this.size);
}else{
g.setColor(BinClock.this.bgcolor);
g.fillArc(2,(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size,BinClock.this.size,315,90);
g.setColor(BinClock.this.color);
g.drawArc(2,(2+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.size)+((Math.abs(BinClock.this.invert-this.pos))*BinClock.this.gap)),
BinClock.this.size,BinClock.this.size,315,90);
}
}
}
}
}
}
};
this.clock_panel.setBackground(BinClock.this.bgcolor);
if(this.mode==BinClock.MODE_COMPACT){
this.clock_panel.setSize(new Dimension((5+BinClock.this.size),(5+BinClock.this.size)));
this.clock_panel.setMinimumSize(new Dimension((5+BinClock.this.size),(5+BinClock.this.size)));
this.clock_panel.setPreferredSize(new Dimension((5+BinClock.this.size),(5+BinClock.this.size)));
this.clock_panel.setMaximumSize(new Dimension((5+BinClock.this.size),(5+BinClock.this.size)));
}else{
this.clock_panel.setSize(new Dimension((5+BinClock.this.size),(5+(BinClock.this.size*6)+(BinClock.this.gap*5))));
this.clock_panel.setMinimumSize(new Dimension((5+BinClock.this.size),
(5+(BinClock.this.size*6)+(BinClock.this.gap*5))));
this.clock_panel.setPreferredSize(new Dimension((5+BinClock.this.size),
(5+(BinClock.this.size*6)+(BinClock.this.gap*5))));
this.clock_panel.setMaximumSize(new Dimension((5+BinClock.this.size),
(5+(BinClock.this.size*6)+(BinClock.this.gap*5))));
}
return(this.clock_panel);
}
/**
* run() is started by the Tread: it calls a repaint for clock_panel and brings it to the front (if desired)
*/
public void run(){
try{
while(true){
Thread.sleep(BinClock.REFRESH_TIMER);
this.clock_panel.repaint();
if(this.alwaysontop){
this.toFront();
this.transferFocusBackward();
}
}
}catch(Exception ex){
ex.printStackTrace();
}
}
/**
* store() writes all data in the Properties (needed for configuration) to .properties file
*/
private void store(){
if(this.hour24){
this.prop.setProperty("hour24","1");
}else{
this.prop.setProperty("hour24","0");
}
this.prop.setProperty("color",Integer.toHexString(this.color.getRGB()).substring(2,8));
this.prop.setProperty("bgcolor",Integer.toHexString(this.bgcolor.getRGB()).substring(2,8));
this.prop.setProperty("size",Integer.toString(this.store_size));
this.prop.setProperty("xpos",Integer.toString(this.getX()));
this.prop.setProperty("ypos",Integer.toString(this.getY()));
if(this.alwaysontop){
this.prop.setProperty("alwaysontop","1");
}else{
this.prop.setProperty("alwaysontop","0");
}
if(this.rectangle){
this.prop.setProperty("rectangle","1");
}else{
this.prop.setProperty("rectangle","0");
}
if(this.invert==0){
this.prop.setProperty("invert","1");
}else{
this.prop.setProperty("invert","0");
}
this.prop.remove("NO_PROPERTIES");
this.prop.remove("config");
try{
this.prop.store(new FileOutputStream(this.prop_file),null);
}catch(Exception ex){
}
}
/**
* main(String[] args) decides on args.length which constructor is used
* @param args String[] command line arguments
*/
public static void main(String[] args){
if(args.length==0){
new BinClock();
}else{
new BinClock(args);
}
}
}