2 * This file is a part of hildon
4 * Copyright (C) 2005, 2006 Nokia Corporation, all rights reserved.
6 * Contact: Michael Dominic Kostrzewa <michael.kostrzewa@nokia.com>
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public License
10 * as published by the Free Software Foundation; version 2.1 of
11 * the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful, but
14 * WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
26 * SECTION:hildon-number-editor
27 * @short_description: A widget used to enter a number within a pre-defined range.
29 * HildonNumberEditor is used to enter a number from a specific range.
30 * There are two buttons to scroll the value in number field.
31 * Manual input is also possible.
34 * <title>HildonNumberEditor example</title>
36 * number_editor = hildon_number_editor_new (-250, 500);
37 * hildon_number_editor_set_range (number_editor, 0, 100);
46 #include "hildon-number-editor.h"
47 #include <gdk/gdkkeysyms.h>
52 #include "hildon-marshalers.h"
53 #include "hildon-private.h"
54 #include "hildon-defines.h"
55 #include "hildon-enum-types.h"
56 #include "hildon-banner.h"
58 #include "hildon-number-editor-private.h"
60 #define _(String) dgettext("hildon-libs", String)
62 /*Pixel spec defines*/
63 #define NUMBER_EDITOR_HEIGHT 30
65 /* Size of plus and minus buttons */
66 #define BUTTON_HEIGHT 30
68 #define BUTTON_WIDTH 30
71 hildon_number_editor_class_init (HildonNumberEditorClass *editor_class);
74 hildon_number_editor_init (HildonNumberEditor *editor);
77 hildon_number_editor_entry_focusout (GtkWidget *widget,
82 hildon_number_editor_entry_changed (GtkWidget *widget,
86 hildon_number_editor_size_request (GtkWidget *widget,
87 GtkRequisition *requisition);
90 set_widget_allocation (GtkWidget *widget,
92 const GtkAllocation *allocation);
95 hildon_number_editor_size_allocate (GtkWidget *widget,
96 GtkAllocation *allocation);
99 hildon_number_editor_focus (GtkWidget *widget,
100 GtkDirectionType direction);
103 hildon_number_editor_entry_keypress (GtkWidget *widget,
108 hildon_number_editor_button_pressed (GtkWidget *widget,
109 GdkEventButton *event,
113 hildon_number_editor_entry_button_released (GtkWidget *widget,
114 GdkEventButton *event,
117 hildon_number_editor_button_released (GtkWidget *widget,
119 HildonNumberEditor *editor);
121 do_mouse_timeout (HildonNumberEditor *editor);
124 change_numbers (HildonNumberEditor *editor,
128 hildon_number_editor_forall (GtkContainer *container,
129 gboolean include_internals,
130 GtkCallback callback,
131 gpointer callback_data);
134 hildon_number_editor_destroy (GtkObject *self);
137 hildon_number_editor_start_timer (HildonNumberEditor *editor);
140 hildon_number_editor_finalize (GObject *self);
143 hildon_number_editor_range_error (HildonNumberEditor *editor,
144 HildonNumberEditorErrorType type);
147 hildon_number_editor_select_all (HildonNumberEditorPrivate *priv);
150 hildon_number_editor_validate_value (HildonNumberEditor *editor,
151 gboolean allow_intermediate);
154 hildon_number_editor_set_property (GObject * object,
156 const GValue * value,
160 hildon_number_editor_get_property (GObject *object,
176 static GtkContainerClass* parent_class;
178 static guint HildonNumberEditor_signal[LAST_SIGNAL] = {0};
181 * hildon_number_editor_get_type:
183 * Returns GType for HildonNumberEditor.
185 * Returns: HildonNumberEditor type
188 hildon_number_editor_get_type (void)
190 static GType editor_type = 0;
194 static const GTypeInfo editor_info =
196 sizeof (HildonNumberEditorClass),
197 NULL, /* base_init */
198 NULL, /* base_finalize */
199 (GClassInitFunc) hildon_number_editor_class_init,
200 NULL, /* class_finalize */
201 NULL, /* class_data */
202 sizeof (HildonNumberEditor),
204 (GInstanceInitFunc) hildon_number_editor_init,
206 editor_type = g_type_register_static (GTK_TYPE_CONTAINER,
207 "HildonNumberEditor",
214 hildon_number_editor_class_init (HildonNumberEditorClass *editor_class)
216 GtkContainerClass *container_class = GTK_CONTAINER_CLASS (editor_class);
217 GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (editor_class);
218 GObjectClass *gobject_class = G_OBJECT_CLASS (editor_class);
220 g_type_class_add_private (editor_class,
221 sizeof (HildonNumberEditorPrivate));
223 parent_class = g_type_class_peek_parent (editor_class);
225 widget_class->size_request = hildon_number_editor_size_request;
226 widget_class->size_allocate = hildon_number_editor_size_allocate;
227 widget_class->focus = hildon_number_editor_focus;
229 editor_class->range_error = hildon_number_editor_range_error;
231 /* Because we derived our widget from GtkContainer, we should override
233 container_class->forall = hildon_number_editor_forall;
234 GTK_OBJECT_CLASS(editor_class)->destroy = hildon_number_editor_destroy;
235 gobject_class->finalize = hildon_number_editor_finalize;
236 gobject_class->set_property = hildon_number_editor_set_property;
237 gobject_class->get_property = hildon_number_editor_get_property;
240 * HildonNumberEditor:value:
242 * The current value of the number editor.
244 g_object_class_install_property (gobject_class, PROP_VALUE,
245 g_param_spec_int ("value",
247 "The current value of number editor",
250 0, G_PARAM_READWRITE));
252 HildonNumberEditor_signal[RANGE_ERROR] =
253 g_signal_new ("range_error", HILDON_TYPE_NUMBER_EDITOR,
254 G_SIGNAL_RUN_LAST, G_STRUCT_OFFSET
255 (HildonNumberEditorClass, range_error),
256 g_signal_accumulator_true_handled, NULL,
257 _hildon_marshal_BOOLEAN__ENUM,
258 G_TYPE_BOOLEAN, 1, HILDON_TYPE_NUMBER_EDITOR_ERROR_TYPE);
262 hildon_number_editor_forall (GtkContainer *container,
263 gboolean include_internals,
264 GtkCallback callback,
265 gpointer callback_data)
267 HildonNumberEditorPrivate *priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (container);
269 g_assert (callback != NULL);
272 if (! include_internals)
275 /* Enumerate child widgets */
276 (*callback) (priv->minus, callback_data);
277 (*callback) (priv->num_entry, callback_data);
278 (*callback) (priv->plus, callback_data);
282 hildon_number_editor_destroy (GtkObject *self)
284 HildonNumberEditorPrivate *priv;
286 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (self);
289 /* Free child widgets */
292 gtk_widget_unparent (priv->minus);
297 gtk_widget_unparent (priv->num_entry);
298 priv->num_entry = NULL;
302 gtk_widget_unparent (priv->plus);
306 if (GTK_OBJECT_CLASS (parent_class)->destroy)
307 GTK_OBJECT_CLASS (parent_class)->destroy(self);
311 hildon_number_editor_stop_repeat_timer (HildonNumberEditorPrivate *priv)
313 g_assert (priv != NULL);
315 if (priv->button_event_id)
317 g_source_remove (priv->button_event_id);
318 priv->button_event_id = 0;
323 hildon_number_editor_finalize (GObject *self)
325 HildonNumberEditorPrivate *priv;
327 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (self);
331 hildon_number_editor_stop_repeat_timer (priv);
333 if (priv->select_all_idle_id)
334 g_source_remove (priv->select_all_idle_id);
336 /* Call parent class finalize, if have one */
337 if (G_OBJECT_CLASS (parent_class)->finalize)
338 G_OBJECT_CLASS (parent_class)->finalize(self);
342 hildon_number_editor_init (HildonNumberEditor *editor)
344 HildonNumberEditorPrivate *priv;
346 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
349 GTK_WIDGET_SET_FLAGS (GTK_WIDGET (editor), GTK_NO_WINDOW);
351 /* Create child widgets */
352 priv->num_entry = gtk_entry_new ();
353 priv->minus = gtk_button_new ();
354 priv->plus = gtk_button_new ();
356 gtk_widget_set_name (priv->minus, "ne-minus-button");
357 gtk_widget_set_name (priv->plus, "ne-plus-button" );
358 gtk_widget_set_size_request (priv->minus, BUTTON_WIDTH, BUTTON_HEIGHT);
359 gtk_widget_set_size_request (priv->plus, BUTTON_WIDTH, BUTTON_HEIGHT);
360 gtk_entry_set_alignment (GTK_ENTRY(priv->num_entry), 1);
362 GTK_WIDGET_UNSET_FLAGS (priv->minus, GTK_CAN_FOCUS);
363 GTK_WIDGET_UNSET_FLAGS (priv->plus, GTK_CAN_FOCUS);
365 priv->button_event_id = 0;
366 priv->select_all_idle_id = 0;
368 gtk_widget_set_parent (priv->minus, GTK_WIDGET (editor));
369 gtk_widget_set_parent (priv->num_entry, GTK_WIDGET (editor));
370 gtk_widget_set_parent (priv->plus, GTK_WIDGET (editor));
372 /* Connect child widget signals */
373 g_signal_connect (GTK_OBJECT (priv->num_entry), "changed",
374 G_CALLBACK (hildon_number_editor_entry_changed),
377 g_signal_connect (GTK_OBJECT (priv->num_entry), "focus-out-event",
378 G_CALLBACK (hildon_number_editor_entry_focusout),
381 g_signal_connect (GTK_OBJECT (priv->num_entry), "key-press-event",
382 G_CALLBACK (hildon_number_editor_entry_keypress),
385 g_signal_connect (GTK_OBJECT (priv->num_entry), "button-release-event",
386 G_CALLBACK (hildon_number_editor_entry_button_released),
389 g_signal_connect (GTK_OBJECT (priv->minus), "button-press-event",
390 G_CALLBACK (hildon_number_editor_button_pressed),
393 g_signal_connect (GTK_OBJECT (priv->plus), "button-press-event",
394 G_CALLBACK (hildon_number_editor_button_pressed),
397 g_signal_connect (GTK_OBJECT (priv->minus), "button-release-event",
398 G_CALLBACK (hildon_number_editor_button_released),
401 g_signal_connect (GTK_OBJECT (priv->plus), "button-release-event",
402 G_CALLBACK (hildon_number_editor_button_released),
405 g_signal_connect (GTK_OBJECT (priv->minus), "leave-notify-event",
406 G_CALLBACK(hildon_number_editor_button_released),
409 g_signal_connect (GTK_OBJECT (priv->plus), "leave-notify-event",
410 G_CALLBACK (hildon_number_editor_button_released),
414 g_object_set (G_OBJECT (priv->num_entry),
415 "hildon-input-mode", HILDON_GTK_INPUT_MODE_NUMERIC, NULL);
418 gtk_widget_show (priv->num_entry);
419 gtk_widget_show (priv->minus);
420 gtk_widget_show (priv->plus);
422 hildon_number_editor_set_range (editor, G_MININT, G_MAXINT);
426 hildon_number_editor_entry_button_released (GtkWidget *widget,
427 GdkEventButton *event,
430 gtk_editable_select_region (GTK_EDITABLE (widget), 0, -1);
435 hildon_number_editor_button_released (GtkWidget *widget,
437 HildonNumberEditor *editor)
439 HildonNumberEditorPrivate *priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
442 hildon_number_editor_stop_repeat_timer (priv);
446 /* Format given number to editor field, no checks performed, all signals
447 are sent normally. */
449 hildon_number_editor_real_set_value (HildonNumberEditorPrivate *priv,
452 /* FIXME: That looks REALLY bad */
455 /* Update text in entry to new value */
456 g_snprintf (buffer, sizeof (buffer), "%d", value);
457 gtk_entry_set_text (GTK_ENTRY (priv->num_entry), buffer);
461 hildon_number_editor_button_pressed (GtkWidget *widget,
462 GdkEventButton *event,
465 /* FIXME: XXX Why aren't we using hildon_number_editor_start_timer here? XXX */
466 /* Need to fetch current value from entry and increment or decrement
469 HildonNumberEditor *editor;
470 HildonNumberEditorPrivate *priv;
471 GtkSettings *settings;
474 g_assert (HILDON_IS_NUMBER_EDITOR (data));
476 editor = HILDON_NUMBER_EDITOR (data);
477 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
480 settings = gtk_settings_get_default ();
481 g_object_get (settings, "gtk-timeout-initial", &timeout, NULL);
483 /* Save type of button pressed */
484 if (GTK_BUTTON (widget) == GTK_BUTTON (priv->plus))
485 priv->button_type = 1;
487 priv->button_type = -1;
489 /* Start repetition timer */
490 if (! priv->button_event_id)
492 change_numbers (editor, priv->button_type);
493 priv->button_event_id = g_timeout_add (timeout,
494 (GSourceFunc) hildon_number_editor_start_timer,
502 hildon_number_editor_start_timer (HildonNumberEditor *editor)
504 HildonNumberEditorPrivate *priv;
505 GtkSettings *settings;
508 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
509 settings = gtk_settings_get_default ();
510 g_object_get (settings, "gtk-timeout-repeat", &timeout, NULL);
513 priv->button_event_id = g_timeout_add (timeout,
514 (GSourceFunc) do_mouse_timeout,
521 do_mouse_timeout (HildonNumberEditor *editor)
523 HildonNumberEditorPrivate *priv;
524 g_assert (HILDON_IS_NUMBER_EDITOR (editor));
526 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
529 GDK_THREADS_ENTER ();
531 /* Update value based on button held */
532 change_numbers (editor, priv->button_type);
534 GDK_THREADS_LEAVE ();
539 /* Changes the current number value by the amount of update
540 and verifies the result. */
542 change_numbers (HildonNumberEditor *editor,
545 HildonNumberEditorPrivate *priv;
548 g_assert (HILDON_IS_NUMBER_EDITOR (editor));
550 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
553 current_value = hildon_number_editor_get_value (editor);
555 /* We need to rerun validation by hand, since validation
556 done in "changed" callback allows intermediate values */
557 hildon_number_editor_real_set_value (priv, current_value + update);
558 hildon_number_editor_validate_value (editor, FALSE);
559 g_object_notify (G_OBJECT (editor), "value");
563 add_select_all_idle (HildonNumberEditorPrivate *priv)
567 if (! priv->select_all_idle_id)
569 priv->select_all_idle_id =
570 g_idle_add((GSourceFunc) hildon_number_editor_select_all, priv);
575 hildon_number_editor_validate_value (HildonNumberEditor *editor,
576 gboolean allow_intermediate)
578 HildonNumberEditorPrivate *priv;
579 gint error_code, fixup_value;
585 g_assert (HILDON_IS_NUMBER_EDITOR(editor));
587 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
590 text = gtk_entry_get_text (GTK_ENTRY (priv->num_entry));
592 fixup_value = priv->default_val;
596 /* Try to convert entry text to number */
597 value = strtol (text, &tail, 10);
599 /* Check if conversion succeeded */
602 /* Check if value is in allowed range. This is tricky in those
603 cases when user is editing a value.
604 For example: Range = [100, 500] and user have just inputted "4".
605 This should not lead into error message. Otherwise value is
606 resetted back to "100" and next "4" press will reset it back
608 if (allow_intermediate)
610 /* We now have the following error cases:
611 * If inputted value as above maximum and
612 maximum is either positive or then maximum
613 negative and value is positive.
614 * If inputted value is below minimum and minimum
615 is negative or minumum positive and value
617 In all other cases situation can be fixed just by
618 adding new numbers to the string.
620 if (value > priv->end && (priv->end >= 0 || (priv->end < 0 && value >= 0)))
622 error_code = HILDON_NUMBER_EDITOR_ERROR_MAXIMUM_VALUE_EXCEED;
623 fixup_value = priv->end;
625 else if (value < priv->start && (priv->start < 0 || (priv->start >= 0 && value <= 0)))
627 error_code = HILDON_NUMBER_EDITOR_ERROR_MINIMUM_VALUE_EXCEED;
628 fixup_value = priv->start;
633 if (value > priv->end) {
634 error_code = HILDON_NUMBER_EDITOR_ERROR_MAXIMUM_VALUE_EXCEED;
635 fixup_value = priv->end;
637 else if (value < priv->start) {
638 error_code = HILDON_NUMBER_EDITOR_ERROR_MINIMUM_VALUE_EXCEED;
639 fixup_value = priv->start;
643 /* The only valid case when conversion can fail is when we
644 have plain '-', intermediate forms are allowed AND
645 minimum bound is negative */
646 else if (! allow_intermediate || strcmp (text, "-") != 0 || priv->start >= 0)
647 error_code = HILDON_NUMBER_EDITOR_ERROR_ERRONEOUS_VALUE;
649 else if (! allow_intermediate)
650 error_code = HILDON_NUMBER_EDITOR_ERROR_ERRONEOUS_VALUE;
652 if (error_code != -1)
654 /* If entry is empty and intermediate forms are nor allowed,
656 /* Change to default value */
657 hildon_number_editor_set_value (editor, fixup_value);
658 g_signal_emit (editor, HildonNumberEditor_signal[RANGE_ERROR], 0, error_code, &r);
659 add_select_all_idle (priv);
664 hildon_number_editor_entry_changed (GtkWidget *widget,
667 g_assert (HILDON_IS_NUMBER_EDITOR (data));
668 hildon_number_editor_validate_value (HILDON_NUMBER_EDITOR (data), TRUE);
669 g_object_notify (G_OBJECT (data), "value");
673 hildon_number_editor_size_request (GtkWidget *widget,
674 GtkRequisition *requisition)
676 HildonNumberEditor *editor;
677 HildonNumberEditorPrivate *priv;
680 editor = HILDON_NUMBER_EDITOR (widget);
681 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
684 /* Requested size is size of all child widgets plus border space */
685 gtk_widget_size_request (priv->minus, &req);
686 requisition->width = req.width;
688 gtk_widget_size_request (priv->num_entry, &req);
689 requisition->width += req.width;
691 gtk_widget_size_request (priv->plus, &req);
692 requisition->width += req.width;
694 requisition->width += HILDON_MARGIN_DEFAULT * 2;
696 /* FIXME: XXX Height is fixed */
697 requisition->height = NUMBER_EDITOR_HEIGHT;
700 /* Update alloc->width so widget fits, update alloc->x to point to free space */
702 set_widget_allocation (GtkWidget *widget,
703 GtkAllocation *alloc,
704 const GtkAllocation *allocation)
706 GtkRequisition child_requisition;
708 gtk_widget_get_child_requisition (widget, &child_requisition);
710 /* Fit to widget width */
711 if (allocation->width + allocation->x > alloc->x + child_requisition.width)
712 alloc->width = child_requisition.width;
715 alloc->width = allocation->width - (alloc->x - allocation->x);
716 if (alloc->width < 0)
720 gtk_widget_size_allocate (widget, alloc);
721 /* Update x position */
722 alloc->x += alloc->width;
726 hildon_number_editor_size_allocate (GtkWidget *widget,
727 GtkAllocation *allocation)
729 HildonNumberEditor *editor;
730 HildonNumberEditorPrivate *priv;
733 editor = HILDON_NUMBER_EDITOR (widget);
734 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
737 widget->allocation = *allocation;
739 /* Add upper border */
740 alloc.y = widget->allocation.y + widget->style->ythickness;
743 if (widget->allocation.height > NUMBER_EDITOR_HEIGHT)
745 alloc.height = NUMBER_EDITOR_HEIGHT - widget->style->ythickness * 2;
746 alloc.y += (widget->allocation.height - NUMBER_EDITOR_HEIGHT) / 2;
749 alloc.height = widget->allocation.height - widget->style->ythickness * 2;
751 if (alloc.height < 0)
754 /* Add left border */
755 alloc.x = allocation->x + widget->style->xthickness;
757 /* Allocate positions for widgets (left-to-right) */
758 set_widget_allocation(priv->minus, &alloc, &widget->allocation);
759 alloc.x += HILDON_MARGIN_DEFAULT;
761 set_widget_allocation(priv->num_entry, &alloc, &widget->allocation);
762 alloc.x += HILDON_MARGIN_DEFAULT;
764 set_widget_allocation(priv->plus, &alloc, &widget->allocation);
768 hildon_number_editor_focus (GtkWidget *widget,
769 GtkDirectionType direction)
772 GtkDirectionType effective_direction;
774 g_assert (HILDON_IS_NUMBER_EDITOR (widget));
776 retval = hildon_private_composite_focus (widget, direction, &effective_direction);
779 return GTK_WIDGET_CLASS (parent_class)->focus (widget, effective_direction);
785 hildon_number_editor_entry_focusout (GtkWidget *widget,
786 GdkEventFocus *event,
789 g_assert (HILDON_IS_NUMBER_EDITOR(data));
791 hildon_number_editor_validate_value (HILDON_NUMBER_EDITOR(data), FALSE);
796 hildon_number_editor_entry_keypress (GtkWidget *widget,
800 GtkEditable *editable;
803 g_assert (HILDON_IS_NUMBER_EDITOR (data));
805 editable = GTK_EDITABLE (widget);
806 cursor_pos = gtk_editable_get_position (editable);
808 switch (event->keyval)
811 /* If the cursor is on the left, try to decrement */
812 if (cursor_pos == 0) {
813 change_numbers (HILDON_NUMBER_EDITOR (data), -1);
819 /* If the cursor is on the right, try to increment */
820 if (cursor_pos >= g_utf8_strlen(gtk_entry_get_text (GTK_ENTRY (widget)), -1))
822 change_numbers (HILDON_NUMBER_EDITOR (data), 1);
823 gtk_editable_set_position(editable, cursor_pos);
836 hildon_number_editor_range_error (HildonNumberEditor *editor,
837 HildonNumberEditorErrorType type)
841 gchar *err_msg = NULL;
842 HildonNumberEditorPrivate *priv;
844 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
850 /* Construct error message */
853 case HILDON_NUMBER_EDITOR_ERROR_MAXIMUM_VALUE_EXCEED:
854 err_msg = g_strdup_printf (_("ckct_ib_maximum_value"), max, max);
857 case HILDON_NUMBER_EDITOR_ERROR_MINIMUM_VALUE_EXCEED:
858 err_msg = g_strdup_printf (_("ckct_ib_minimum_value"), min, min);
861 case HILDON_NUMBER_EDITOR_ERROR_ERRONEOUS_VALUE:
863 g_strdup_printf (_("ckct_ib_set_a_value_within_range"), min, max);
867 /* Infoprint error */
870 hildon_banner_show_information (GTK_WIDGET (GTK_WINDOW (gtk_widget_get_ancestor (GTK_WIDGET(editor),
871 GTK_TYPE_WINDOW))), NULL, err_msg);
879 * hildon_number_editor_new:
880 * @min: minimum accepted value
881 * @max: maximum accepted value
883 * Creates new number editor
885 * Returns: a new #HildonNumberEditor widget
888 hildon_number_editor_new (gint min,
891 HildonNumberEditor *editor = g_object_new (HILDON_TYPE_NUMBER_EDITOR, NULL);
893 /* Set user inputted range to editor */
894 hildon_number_editor_set_range (editor, min, max);
896 return GTK_WIDGET (editor);
900 * hildon_number_editor_set_range:
901 * @editor: a #HildonNumberEditor widget
902 * @min: minimum accepted value
903 * @max: maximum accepted value
905 * Sets accepted number range for editor
908 hildon_number_editor_set_range (HildonNumberEditor *editor,
912 HildonNumberEditorPrivate *priv;
913 gchar buffer_min[32], buffer_max[32];
916 g_return_if_fail (HILDON_IS_NUMBER_EDITOR (editor));
918 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
921 /* Set preferences */
922 priv->start = MIN (min, max);
923 priv->end = MAX (min, max);
925 /* Find maximum allowed length of value */
926 g_snprintf (buffer_min, sizeof (buffer_min), "%d", min);
927 g_snprintf (buffer_max, sizeof (buffer_max), "%d", max);
928 a = strlen (buffer_min);
929 b = strlen (buffer_max);
931 /* Set maximum size of entry */
932 gtk_entry_set_width_chars (GTK_ENTRY (priv->num_entry), MAX (a, b));
933 hildon_number_editor_set_value (editor, priv->start);
937 * hildon_number_editor_get_value:
938 * @editor: pointer to #HildonNumberEditor
940 * Returns: current NumberEditor value
943 hildon_number_editor_get_value (HildonNumberEditor *editor)
945 HildonNumberEditorPrivate *priv;
947 g_return_val_if_fail (HILDON_IS_NUMBER_EDITOR (editor), 0);
949 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
952 return atoi (gtk_entry_get_text (GTK_ENTRY (priv->num_entry)));
956 * hildon_number_editor_set_value:
957 * @editor: pointer to #HildonNumberEditor
958 * @value: numeric value for number editor
960 * Sets numeric value for number editor
963 hildon_number_editor_set_value (HildonNumberEditor *editor,
966 HildonNumberEditorPrivate *priv;
968 g_return_if_fail (HILDON_IS_NUMBER_EDITOR (editor));
970 priv = HILDON_NUMBER_EDITOR_GET_PRIVATE (editor);
973 g_return_if_fail (value <= priv->end);
974 g_return_if_fail (value >= priv->start);
976 priv->default_val = value;
977 hildon_number_editor_real_set_value (priv, value);
978 g_object_notify (G_OBJECT(editor), "value");
981 /* When calling gtk_entry_set_text, the entry widget does things that can
982 * cause the whole widget to redraw. This redrawing is delayed and if any
983 * selections are made right after calling the gtk_entry_set_text the
984 * setting of the selection might seem to have no effect.
986 * If the selection is delayed with a lower priority than the redrawing,
987 * the selection should stick. Calling this function with g_idle_add should
991 hildon_number_editor_select_all (HildonNumberEditorPrivate *priv)
993 GDK_THREADS_ENTER ();
994 gtk_editable_select_region (GTK_EDITABLE (priv->num_entry), 0, -1);
995 priv->select_all_idle_id = 0;
996 GDK_THREADS_LEAVE ();
1001 hildon_number_editor_set_property (GObject *object,
1003 const GValue *value,
1006 HildonNumberEditor *editor;
1008 editor = HILDON_NUMBER_EDITOR (object);
1013 hildon_number_editor_set_value (editor, g_value_get_int (value));
1017 G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
1023 hildon_number_editor_get_property (GObject *object,
1028 HildonNumberEditor *editor;
1030 editor = HILDON_NUMBER_EDITOR (object);
1035 g_value_set_int(value, hildon_number_editor_get_value (editor));
1039 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);