--- gnome-panel-2.18.1/applets/clock/clock.c	2007-10-12 17:06:51.000000000 +0800
+++ gnome-panel-2.18.1.new/applets/clock/clock.c	2007-10-12 15:46:31.000000000 +0800
@@ -52,6 +52,7 @@
 #include <langinfo.h>
 #endif
 #include <sys/time.h>
+#include <math.h>
 
 #include <panel-applet.h>
 #include <panel-applet-gconf.h>
@@ -113,7 +114,7 @@ struct _ClockData {
 	/* widgets */
 	GtkWidget *applet;
 	GtkWidget *clockw;
-        GtkWidget *toggle;
+        /* GtkWidget *toggle; */
 	GtkWidget *props;
 	GtkWidget *about;
         GtkWidget *calendar_popup;
@@ -151,6 +152,11 @@ struct _ClockData {
 
 	int fixed_width;
 	int fixed_height;
+	int width;
+	int height;
+	int face_size;
+
+	int toggle;
 
         GtkWidget *showseconds_check;
         GtkWidget *showdate_check;
@@ -189,9 +195,17 @@ static void update_orient (ClockData *cd
 static void
 unfix_size (ClockData *cd)
 {
-	cd->fixed_width = -1;
-	cd->fixed_height = -1;
-	gtk_widget_queue_resize (cd->toggle);
+	int vertical = 0;
+        if (cd->orient == PANEL_APPLET_ORIENT_LEFT ||cd->orient == PANEL_APPLET_ORIENT_RIGHT)
+		vertical = 1;
+
+	if (vertical) 
+		gtk_widget_set_size_request(cd->applet, -1, cd->size -3);
+	else
+		gtk_widget_set_size_request(cd->applet, cd->size -3, -1);
+	//cd->fixed_width = -1;
+	//cd->fixed_height = -1;
+	//gtk_widget_queue_resize (cd->toggle);
 }
 
 static int
@@ -271,6 +285,7 @@ clock_timeout_callback (gpointer data)
 
         time (&new_time);
 
+	/*
 	if (!cd->showseconds &&
 	    cd->format != CLOCK_FORMAT_UNIX &&
 	    cd->format != CLOCK_FORMAT_CUSTOM) {
@@ -286,6 +301,8 @@ clock_timeout_callback (gpointer data)
 	} else {
 		update_clock (cd);
 	}
+	*/
+	update_clock (cd);
 
 	clock_set_timeout (cd);
 
@@ -348,7 +365,7 @@ calculate_minimum_height (GtkWidget     
 static gboolean
 use_two_line_format (ClockData *cd)
 {
-        if (cd->size >= 2 * calculate_minimum_height (cd->toggle, cd->orient))
+        if (cd->size >= 2 * calculate_minimum_height (cd->clockw, cd->orient))
                 return TRUE;
 
         return FALSE;
@@ -450,10 +467,87 @@ set_atk_name_description (GtkWidget  *wi
 		atk_object_set_name (obj, name);
 }
 
-static void
-update_clock (ClockData * cd)
-{
-	struct tm *tm;
+#define DRAW_LINE(red,green,blue,line_width,inner_radius,outer_radius,angle_60ths) \
+  h =  sin ((angle_60ths) * M_PI / 30);                                        \
+  v = -cos ((angle_60ths) * M_PI / 30);                                       \
+                                                                                   \
+  cairo_save (cr);                                                                 \
+  cairo_set_source_rgb (cr, red, green, blue);                                     \
+  cairo_set_line_width (cr, (line_width) * cairo_get_line_width (cr));               \
+  cairo_move_to (cr,                                                               \
+		 cd->width  / 2 + (inner_radius) * radius * h,               \
+		 cd->height / 2 + (inner_radius) * radius * v);              \
+  cairo_line_to (cr,                                                               \
+		 cd->width  / 2 + (outer_radius) * radius * h,               \
+		 cd->height / 2 + (outer_radius) * radius * v);              \
+  cairo_stroke (cr);                                                               \
+  cairo_restore (cr);                                                              
+
+#define DRAW_HAND(red,green,blue,blob_radius, outer_radius,angle_60ths) \
+  h =  sin ((angle_60ths) * M_PI / 30);                                        \
+  v = -cos ((angle_60ths) * M_PI / 30);                                       \
+                                                                                   \
+  cairo_save (cr);                                                                 \
+  cairo_set_source_rgb (cr, red, green, blue);                                     \
+  cairo_arc_negative(cr, cd->width/2, cd->height/2, (blob_radius) * radius,\
+	        (angle_60ths)*M_PI/30 - M_PI,  \
+	        (angle_60ths)*M_PI/30);  \
+  cairo_arc_negative (cr,                                                               \
+		 cd->width  / 2 + (outer_radius) * radius * h,               \
+		 cd->height / 2 + (outer_radius) * radius * v,               \
+		 0.3*(blob_radius)*radius, \
+	        (angle_60ths)*M_PI/30,  \
+	        (angle_60ths)*M_PI/30 + M_PI);  \
+  cairo_fill (cr);                                                               \
+  cairo_restore (cr);                                                              
+
+static gboolean expose_callback(GtkWidget *widget, GdkEventExpose *event, ClockData * cd){
+  int i;
+  char date[256];
+  char *utf8, *loc;
+  struct tm *tm;
+  double h,v;
+	
+  time (&cd->current_time);
+
+  if (cd->gmt_time)
+    tm = gmtime (&cd->current_time);
+  else
+    tm = localtime (&cd->current_time);
+
+  cairo_t *cr = gdk_cairo_create (cd->clockw->window);
+
+  int radius = cd->face_size/2;
+  cairo_set_line_width(cr, 1);
+  cairo_set_line_cap(cr, CAIRO_LINE_CAP_ROUND);
+
+  cairo_arc (cr, cd->width / 2, cd->height / 2, radius, 0, 2 * M_PI);
+  cairo_set_source_rgb (cr, 0.95, 0.95, 0.95);
+  cairo_fill_preserve (cr);
+
+  cairo_set_source_rgb (cr, 0, 0, 0);
+  cairo_stroke (cr);
+
+  cairo_arc (cr, cd->width / 2, cd->height / 2, 0.5 * radius, 0, 2 * M_PI);
+  cairo_set_source_rgb (cr, 0.75, 0.75, 0.8);
+  cairo_fill (cr);
+
+  for (i = 0; i < 4; i++)
+    {
+      double inset, width;
+      inset = 0.2;
+      width = 1;
+      DRAW_LINE(0, 0, 0, width, 1.0 - inset, 1.0, i * 15); 
+    }
+
+  DRAW_HAND(0,     0,   0, 0.12,   0.6,tm->tm_hour * 5 + tm->tm_min / 12.0); 
+  DRAW_HAND(0.1, 0.1, 0.1, 0.08,   0.9,tm->tm_min + tm->tm_sec / 60.0);
+  DRAW_LINE(1,     0,   0, 1.0, 0, 0.8,tm->tm_sec);
+
+  cairo_destroy (cr);
+  cr = NULL;
+
+/*	struct tm *tm;
 	char date[256], hour[256];
 	char *utf8, *loc;
 	gboolean use_markup;
@@ -523,8 +617,10 @@ update_clock (ClockData * cd)
 
 	update_orient (cd);
 	gtk_widget_queue_resize (cd->toggle);
+	*/
 
-        if (!cd->showdate) {
+        /* if (!cd->showdate) { */
+	if (1) {
                 /* Show date in tooltip */
                 loc = g_locale_from_utf8 (_("%A %B %d"), -1, NULL, NULL, NULL);
                 if (!loc)
@@ -534,28 +630,35 @@ update_clock (ClockData * cd)
                 g_free (loc);
 
                 utf8 = g_locale_to_utf8 (date, -1, NULL, NULL, NULL);
-                set_tooltip (cd->applet, cd->toggle, utf8);
+                set_tooltip (cd->applet, cd->clockw, utf8);
                 g_free (utf8);
         } else {
 #ifdef HAVE_LIBECAL
-                set_tooltip (cd->applet, cd->toggle, _("Click to view your appointments and tasks"));
+                set_tooltip (cd->applet, cd->clockw, _("Click to view your appointments and tasks"));
 #else
-                set_tooltip (cd->applet, cd->toggle, _("Click to view month calendar"));
+                set_tooltip (cd->applet, cd->clockw, _("Click to view month calendar"));
 #endif
         }
 }
 
+
+static void
+update_clock (ClockData * cd)
+{
+  gtk_widget_queue_draw (cd->clockw);
+}
+
 static void
 refresh_clock (ClockData *cd)
 {
-	unfix_size (cd);
+	// unfix_size (cd);
 	update_clock (cd);
 }
 
 static void
 refresh_clock_timeout(ClockData *cd)
 {
-	unfix_size (cd);
+	// unfix_size (cd);
 	
 	update_timeformat (cd);
 
@@ -628,7 +731,8 @@ close_on_escape (GtkWidget   *widget,
 		 ClockData   *cd)
 {
 	if (event->keyval == GDK_Escape) {
-		gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (cd->toggle), FALSE);
+		// gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (cd->toggle), FALSE);
+		cd->toggle = FALSE;
 		return TRUE;
 	}
 
@@ -640,7 +744,8 @@ delete_event (GtkWidget   *widget,
 	      GdkEvent    *event,
 	      ClockData   *cd)
 {
-	gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (cd->toggle), FALSE);
+	// gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (cd->toggle), FALSE);
+	cd->toggle = FALSE;
 	return TRUE;
 }
 
@@ -1694,7 +1799,8 @@ present_calendar_popup (ClockData *cd,
 static void
 update_popup (ClockData *cd)
 {
-        if (!gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (cd->toggle))) {
+        // if (!gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (cd->toggle))) {
+        if (!cd->toggle) {
                 if (cd->calendar_popup)
                         gtk_widget_destroy (cd->calendar_popup);
                 cd->calendar_popup = NULL;
@@ -1707,13 +1813,13 @@ update_popup (ClockData *cd)
                                            (gpointer *) &cd->calendar_popup);
         }
 
-        if (cd->calendar_popup && GTK_WIDGET_REALIZED (cd->toggle)) {
+        if (cd->calendar_popup && GTK_WIDGET_REALIZED (cd->clockw)) {
 #ifdef HAVE_LIBECAL
                 if (cd->tasks_filter && cd->task_list)
                         gtk_tree_model_filter_refilter (cd->tasks_filter);
 #endif
 
-                present_calendar_popup (cd, cd->calendar_popup, cd->toggle);
+                present_calendar_popup (cd, cd->calendar_popup, cd->clockw);
                 gtk_window_present (GTK_WINDOW (cd->calendar_popup));
         }
 }
@@ -1722,15 +1828,21 @@ static void
 toggle_calendar (GtkWidget *button,
                  ClockData *cd)
 {
+	cd->toggle = !cd->toggle;
 	update_popup (cd);
 }
 
 static gboolean
 do_not_eat_button_press (GtkWidget      *widget,
-                         GdkEventButton *event)
+                         GdkEventButton *event,
+                         ClockData *cd)
 {
 	if (event->button != 1)
 		g_signal_stop_emission_by_name (widget, "button_press_event");
+	else {
+		cd->toggle = !cd->toggle;
+		update_popup (cd);
+	}
 
 	return FALSE;
 }
@@ -1763,6 +1875,17 @@ clock_update_text_gravity (GtkWidget *la
 	pango_context_set_base_gravity (context, PANGO_GRAVITY_AUTO);
 }
 
+static void
+clock_size_allocate (GtkWidget *clock, GtkAllocation *alloc, gpointer data)
+{
+	ClockData *cd = data;
+
+	cd->width = alloc->width;
+	cd->height = alloc->height;
+	cd->face_size = alloc->width < alloc->height ? alloc->width : alloc->height;
+
+}
+
 static inline void
 force_no_focus_padding (GtkWidget *widget)
 {
@@ -1788,23 +1911,39 @@ static void
 create_clock_widget (ClockData *cd)
 {
 	GtkWidget *clock;
-	GtkWidget *toggle;
-	GtkWidget *alignment;
+	// GtkWidget *toggle;
+	// GtkWidget *alignment;
 
-	clock = gtk_label_new ("hmm?");
+	// clock = gtk_label_new ("hmm?");
+	clock = gtk_drawing_area_new();
 	g_signal_connect (clock, "size_request",
 			  G_CALLBACK (clock_size_request),
 			  cd);
+	g_signal_connect (clock, "size_allocate",
+			  G_CALLBACK (clock_size_allocate),
+			  cd);
 	g_signal_connect_swapped (clock, "style_set",
 				  G_CALLBACK (unfix_size),
 				  cd);
-	gtk_label_set_justify (GTK_LABEL (clock), GTK_JUSTIFY_CENTER);
+	g_signal_connect (G_OBJECT (clock),
+		    "expose_event",
+		    G_CALLBACK (expose_callback),
+		    cd);
+	gtk_widget_add_events(clock, GDK_ENTER_NOTIFY_MASK |
+			             GDK_LEAVE_NOTIFY_MASK |
+				     GDK_BUTTON_PRESS_MASK);
+	
+	g_signal_connect (clock, "button_press_event",
+			  G_CALLBACK (do_not_eat_button_press), cd);
+
+	// gtk_label_set_justify (GTK_LABEL (clock), GTK_JUSTIFY_CENTER);
 	clock_update_text_gravity (clock);
 	g_signal_connect (clock, "screen-changed",
 			  G_CALLBACK (clock_update_text_gravity),
 			  NULL);
 	gtk_widget_show (clock);
 
+	/*
 	toggle = gtk_toggle_button_new ();
 	gtk_container_set_resize_mode (GTK_CONTAINER (toggle), GTK_RESIZE_IMMEDIATE);
 	gtk_button_set_relief (GTK_BUTTON (toggle), GTK_RELIEF_NONE);
@@ -1826,6 +1965,7 @@ create_clock_widget (ClockData *cd)
 	gtk_widget_show (toggle);
 
 	cd->toggle = toggle;
+	*/
 
 	cd->clockw = clock;
 
@@ -1855,13 +1995,13 @@ update_orient (ClockData *cd)
 	gdouble      angle;
 
 	text = gtk_label_get_text (GTK_LABEL (cd->clockw));
-	min_width = calculate_minimum_width (cd->toggle, text);
+	min_width = calculate_minimum_width (cd->clockw, text);
 
 	if (cd->orient == PANEL_APPLET_ORIENT_LEFT &&
-	    min_width > cd->toggle->allocation.width)
+	    min_width > cd->clockw->allocation.width)
 		new_angle = 270;
 	else if (cd->orient == PANEL_APPLET_ORIENT_RIGHT &&
-		 min_width > cd->toggle->allocation.width)
+		 min_width > cd->clockw->allocation.width)
 		new_angle = 90;
 	else
 		new_angle = 0;
@@ -2279,7 +2419,7 @@ show_week_changed (GConfClient  *client,
 						  options);
 
                 position_calendar_popup (clock, clock->calendar_popup,
-					 clock->toggle);
+					 clock->clockw);
 	}
 }
 
@@ -2406,6 +2546,8 @@ fill_clock_applet (PanelApplet *applet)
 	cd->fixed_width = -1;
 	cd->fixed_height = -1;
 
+	cd->toggle = FALSE;
+
 	cd->applet = GTK_WIDGET (applet);
 
 	setup_gconf (cd);
@@ -2452,8 +2594,9 @@ fill_clock_applet (PanelApplet *applet)
 	create_clock_widget (cd);
 
 	gtk_container_set_border_width (GTK_CONTAINER (cd->applet), 0);
-	gtk_container_set_border_width (GTK_CONTAINER (cd->toggle), 0);
-	gtk_container_add (GTK_CONTAINER (cd->applet), cd->toggle);
+	// gtk_container_set_border_width (GTK_CONTAINER (cd->toggle), 0);
+	// gtk_container_add (GTK_CONTAINER (cd->applet), cd->toggle);
+	gtk_container_add (GTK_CONTAINER (cd->applet), cd->clockw);
 
 #ifndef CLOCK_INPROCESS
 	gtk_window_set_default_icon_name (CLOCK_ICON);
@@ -2464,10 +2607,12 @@ fill_clock_applet (PanelApplet *applet)
 	/* we have to bind change_orient before we do applet_widget_add
 	   since we need to get an initial change_orient signal to set our
 	   initial oriantation, and we get that during the _add call */
+	/*
 	g_signal_connect (G_OBJECT (cd->applet),
 			  "change_orient",
 			  G_CALLBACK (applet_change_orient),
 			  cd);
+	*/
 
 	g_signal_connect (G_OBJECT (cd->toggle),
 			  "size_allocate",
