home *** CD-ROM | disk | FTP | other *** search
-
- package sub_arctic.input;
-
- import sub_arctic.lib.interactor;
-
- /**
- * Focus based dispatch agent for delivering text input. This agent dispatches
- * under the text_acceptor input protocol. That protocol provides features
- * for filtering characters, recognizing and acting of special "action
- * characters", and performing standard edit functions (i.e., character delete
- * and line kill) in addition to normal text input.
- *
- * @see sub_arctic.input.text_acceptor
- * @author Scott Hudson
- */
- public class text_focus_agent extends single_focus_agent {
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Simple constructor. */
- public text_focus_agent()
- {
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Handle informing an object that it has become the new text focus.
- * This calls the start_text_entry() method.
- *
- * @param focusable obj the object receiving focus
- * @param event evt the event that "caused" the focus.
- * @param Object user_info the user info to be passed to the object.
- */
- protected void inform_focus_enter(
- focusable obj,
- event evt,
- Object user_info)
- {
- event evt_copy;
-
- /* do a start_text_entry rather than the default focus_set_enter() */
- evt_copy = new event(evt);
- if (obj instanceof interactor)
- evt_copy.global_to_local((interactor)obj);
- else
- evt_copy.reset_to_global();
- ((text_acceptor)obj).start_text_entry(evt_copy, user_info);
- }
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Handle informing an object that it has lost the text focus.
- * This calls the end_text_entry() method.
- *
- * @param focusable obj the object loosing focus
- * @param event evt the event that "caused" the loss of focus.
- * @param Object user_info the user info to be passed to the object.
- */
- protected void inform_focus_exit(
- focusable obj,
- event evt,
- Object user_info)
- {
- event evt_copy;
-
- /* do an end_text_entry rather than the normal focus_set_exit() */
- evt_copy = new event(evt);
- if (obj instanceof interactor)
- evt_copy.global_to_local((interactor)obj);
- else
- evt_copy.reset_to_global();
- ((text_acceptor)obj).end_text_entry(evt_copy, user_info);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** First character to be treated as a "delete character". This can be
- * disabled by setting it to '\0'. Defaults to backspace. Note: once
- * the system allows user preferences for edit character to be determined,
- * this will become protected.
- */
- public char del_char1 = '\b';
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Second character to be treated as a "delete character". This can be
- * disabled by setting it to '\0' or the same as del_char2. Defaults to
- * delete. Note: once the system allows user preferences for edit
- * character to be determined, this will become protected.
- */
- public char del_char2 = (char)127;
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Character to be treated as a "line kill character". This can be disabled
- * by setting it to '\0'. Defaults to ^U ('\025'). Note: once the system
- * allows user preferences for edit character to be determined, this will
- * become protected.
- */
- public char line_kill_char = '\025';
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Indicate whether the given object is suitable to be our focus. In this
- * case it needs to be a text_acceptor object.
- *
- * @param focusable candidate_obj the object being inquired about.
- * @return boolean indicating if the object is suitable.
- */
- public boolean allowable_focus(focusable candidate_obj)
- {
- /* must be a text acceptor */
- return candidate_obj instanceof text_acceptor;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Indicate if the given event is wanted by this agent. Here we are
- * interested in KEY_ACTION and KEY_PRESS events.
- *
- * @param event evt the event being inquired about.
- * @return boolean indicating if we want the event.
- public boolean event_is_useful(event evt)
- {
- return evt.id() == event.KEY_ACTION || evt.id() == event.KEY_PRESS;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Attempt to dispatch the given event as text input.
- *
- * @param event evt the event to dispatch.
- * @param Object user_info ignored (since we are focus agent).
- * @param interactor to_obj ignored (since we are focus agent).
- * @param int seq_num ignored (since we are focus agent).
- * @return boolean indicating if the input was consumed.
- */
- public boolean dispatch_event(
- event evt,
- Object user_info,
- interactor to_obj,
- int seq_num)
- {
- text_acceptor target;
- int filtered;
- event evt_copy;
-
- /* get the focus object and if we don't have one bail now */
- target = (text_acceptor)_focus_set.elementAt(0);
- if (target == null) return false;
-
- /* put event in target object's coords */
- evt_copy = new event(evt);
- if (target instanceof interactor)
- evt_copy.global_to_local((interactor)target);
- else
- evt_copy.reset_to_global();
-
- /* do we have a "regular" key or a special "action" key? */
- if (evt.id() == event.KEY_PRESS)
- {
- /* look for our edit keys first */
- if ((del_char1 != '\0' && del_char1 == evt.key()) ||
- (del_char2 != '\0' && del_char2 == evt.key()))
- return target.delete_char(evt, user_info);
- if (line_kill_char != '\0' && line_kill_char == evt.key())
- return target.line_kill(evt_copy, user_info);
-
- /* its a "regular" character, so filter it */
- filtered = target.char_filter(evt.key(),evt.modifiers());
-
- /* do any special actions that indicates */
- if (filtered == text_acceptor.DISCARD_CHAR) return false;
- if (filtered == text_acceptor.CLOSURE_ACTION_CHAR)
- return target.action_char(evt_copy, (char)evt.key(), user_info);
-
- /* if all else fails dispatch as a normal character */
- return target.new_char(evt_copy, (char)filtered, user_info);
- }
- else
- {
- /* it was an "action" char, dispatch as a special */
- return target.special_key(evt_copy, evt.key(), user_info);
- }
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Standard translation filter for mapping to all upper case. Special
- * values are passed through unaltered, so this filter can be composed with
- * others if desired.
- *
- * @param int ch ordinal value of the character to translate.
- * @return int the ordinal value of the character converted to upper case.
- */
- public static int translate_to_upper(int ch)
- {
- if (ch < 0 || ch > 0xffff) return ch;
- return Character.toUpperCase((char)ch);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Standard translation filter for mapping to all lower case. Special
- * values are passed through unaltered, so this filter can be composed with
- * others if desired.
- *
- * @param int ch ordinal value of the character to translate.
- * @return int the ordinal value of the character converted to lower case.
- */
- public static int translate_to_lower(int ch)
- {
- if (ch < 0 || ch > 0xffff) return ch;
- return Character.toLowerCase((char)ch);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Standard filter that removes all whitespace. As with other filters,
- * this can be composed with other standard filters. For example, one
- * can code something like: <br>
- * <pre>
- * return no_white(eol_action(translate_to_lower(ch)));
- * </pre>
- * @param int ch ordinal value of the character to filter.
- * @return int the ordinal value of the filtered character.
- */
- public static int no_white(int ch)
- {
- if (ch < 0 || ch > 0xffff) return ch;
- if (Character.isSpace((char)ch)) return text_acceptor.DISCARD_CHAR;
- return ch;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Standard filter to accept only decimal digits.
- *
- * @param int ch ordinal value of the character to filter.
- * @return int the ordinal value of the filtered character.
- */
- public static int only_digits(int ch)
- {
- if (ch < 0 || ch > 0xffff) return ch;
- if (!Character.isDigit((char)ch)) return text_acceptor.DISCARD_CHAR;
- return ch;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Standard filter to accept only decimal digits, plus, minus, and decimal
- * point.
- *
- * @param int ch ordinal value of the character to filter.
- * @return int the ordinal value of the filtered character.
- */
- public static int only_numeric(int ch)
- {
- if (ch < 0 || ch > 0xffff) return ch;
- if (!Character.isDigit((char)ch))
- {
- if (ch == '+' || ch == '-' || ch == '.') return ch;
- return text_acceptor.DISCARD_CHAR;
- }
- return ch;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Standard filter to translate end of line characters into closure actions.
- * As with other filters, this can be composed with other standard filters.
- * For example, one can code something like: <br>
- * <pre>
- * return only_digits(eol_action(ch));
- * </pre>
- * @param int ch ordinal value of the character to filter.
- * @return int the ordinal value of the filtered character.
- */
- public static int eol_action(int ch)
- {
- /* catch end of line characters */
- if (ch == '\n' || ch == '\r') return text_acceptor.CLOSURE_ACTION_CHAR;
-
- /* pass everything else */
- return ch;
- }
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
- // later need to add tabbing between fields
- }
- /*=========================== COPYRIGHT NOTICE ===========================
-
- This file is part of the subArctic user interface toolkit.
-
- Copyright (c) 1996 Scott Hudson and Ian Smith
- All rights reserved.
-
- The subArctic system is freely available for most uses under the terms
- and conditions described in
- http://www.cc.gatech.edu/gvu/ui/sub_arctic/sub_arctic/doc/usage.html
- and appearing in full in the lib/interactor.java source file.
-
- The current release and additional information about this software can be
- found starting at: http://www.cc.gatech.edu/gvu/ui/sub_arctic/
-
- ========================================================================*/
-