Advertisement
Guest User

KeyView.cs

a guest
Jan 6th, 2016
185
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 10.33 KB | None | 0 0
  1. using System;
  2. using Android.Content;
  3. using Android.Views;
  4. using Android.Widget;
  5. using Android.Util;
  6. using Android.Graphics;
  7. using System.Threading;
  8.  
  9. namespace Apps.Droid
  10. {
  11.     public class KeyView : View, View.IOnTouchListener
  12.     {
  13.         public static int LongTouchDelay = 800; // .8 seconds
  14.         public static int ShortTouchDelay = 100; // .1 seconds
  15.         public static Color BG_NORMAL,
  16.                             BG_LIGHT, BG_DARK,
  17.                             FG_PRIMARYDARK,
  18.                             FG_PRIMARYLIGHT,
  19.                             FG_SECONDARY;
  20.  
  21.         protected KeyboardView keyboard;
  22.         protected Key key;
  23.         public int width { get; set; }
  24.         public int height { get; set; }
  25.         public bool isDown { get; set; }
  26.  
  27.         public KeyView(Context context, IAttributeSet attrs)
  28.             : base(context, attrs)
  29.         { }
  30.  
  31.         public KeyView(Context context, IAttributeSet attrs, int defStyle)
  32.             : base(context, attrs, defStyle)
  33.         { }
  34.  
  35.         public KeyView(Context context, IAttributeSet attrs, int defStyle, int defStyleRes)
  36.             : base(context, attrs, defStyle, defStyleRes)
  37.         { }
  38.  
  39.         protected override void OnMeasure(int widthMeasureSpec, int heightMeasureSpec)
  40.         {
  41.             base.OnMeasure(widthMeasureSpec, heightMeasureSpec);
  42.            
  43.             SetMeasuredDimension(width, height);
  44.         }
  45.  
  46.         // key views are always dynamically created
  47.         public KeyView(Context ctx, KeyboardView parent, Key k, int leftMargin)
  48.             : base(ctx)
  49.         {
  50.             // make sure the key will draw
  51.             SetWillNotDraw(false);
  52.  
  53.             keyboard = parent;
  54.             key = k;
  55.             isDown = false;
  56.  
  57.             // check for an overridden span to adjust width, if needed
  58.             int span = string.IsNullOrEmpty(key.Span) ? 1 : Convert.ToInt32(key.Span);
  59.             int keyWidth = keyboard.keyWidth + ((span - 1) * keyboard.keyWidth);
  60.  
  61.             width = keyWidth;
  62.             height = keyboard.keyHeight;
  63.  
  64.             // set margin
  65.             var parameters = new LinearLayout.LayoutParams(
  66.                 LinearLayout.LayoutParams.WrapContent,
  67.                 LinearLayout.LayoutParams.MatchParent
  68.             );
  69.             parameters.LeftMargin = leftMargin;
  70.             LayoutParameters = parameters;
  71.  
  72.             // set touch listener
  73.             SetOnTouchListener(this);
  74.  
  75.             // enable haptic feedback for button presses
  76.             HapticFeedbackEnabled = true;
  77.         }
  78.  
  79.         protected override void OnDraw(Canvas canvas)
  80.         {
  81.             base.OnDraw(canvas);
  82.  
  83.             KeyState primary = key.Primary;
  84.             KeyState secondary = key.Secondary;
  85.  
  86.             if (keyboard.swapped)
  87.             {
  88.                 primary = key.Secondary != null ? key.Secondary : key.Primary;
  89.                 secondary = key.Secondary != null ? key.Primary : null;
  90.             }
  91.            
  92.             if (keyboard.shifted)
  93.             {
  94.                 if (primary.Shift != null)
  95.                     primary = primary.Shift;
  96.  
  97.                 if (secondary != null && secondary.Shift != null)
  98.                     secondary = secondary.Shift;
  99.             }
  100.  
  101.             // figure out what color the key is supposed to be
  102.             Paint bg = new Paint(PaintFlags.AntiAlias);
  103.             bg.Color = GetKeyBgColor(key.Style);
  104.             if (Android.OS.Build.VERSION.SdkInt >= Android.OS.BuildVersionCodes.Lollipop)
  105.                 canvas.DrawRoundRect(keyboard.keyMargin, keyboard.keyMargin, width - keyboard.keyMargin, height - keyboard.keyMargin, keyboard.keyMargin, keyboard.keyMargin, bg);
  106.             else
  107.                 canvas.DrawRoundRect(new RectF(keyboard.keyMargin, keyboard.keyMargin, width - keyboard.keyMargin, height - keyboard.keyMargin), keyboard.keyMargin, keyboard.keyMargin, bg);
  108.  
  109.             // draw primary key state
  110.             Paint fg = new Paint(PaintFlags.AntiAlias);
  111.             fg.TextSize = height * .5f;
  112.             fg.Color = GetKeyFgColor(key.Style);
  113.             string character = string.IsNullOrEmpty(primary.Character) ? "#" : primary.Character;
  114.             int charWidth = Convert.ToInt32(fg.MeasureText(character));
  115.             int charX = (width - charWidth) / 2;
  116.             canvas.DrawText(character, charX, (height * .7f), fg);
  117.  
  118.             // draw secondary key state
  119.             if (secondary != null)
  120.             {
  121.                 fg.TextSize = height * .25f;
  122.                 fg.Color = GetKeyFgColor(key.Style, true);
  123.                 character = string.IsNullOrEmpty(secondary.Character) ? "#" : secondary.Character;
  124.                 charWidth = Convert.ToInt32(fg.MeasureText(character));
  125.                 charX = width - charWidth - (keyboard.keyMargin * 2);
  126.                 canvas.DrawText(character, charX, (height * .35f), fg);
  127.             }
  128.         }
  129.  
  130.         protected Color GetKeyBgColor(string style) {
  131.             Color newColor = BG_NORMAL;
  132.  
  133.             if (key.Primary.Id == "shift" && keyboard.superShifted)
  134.                 return Color.Cyan;
  135.  
  136.             if (style != null) {
  137.                 if (style == "light")
  138.                     newColor = BG_LIGHT;
  139.                 else if (style == "dark")
  140.                     newColor = BG_DARK;
  141.             }
  142.  
  143.             return newColor;
  144.         }
  145.  
  146.         protected Color GetKeyFgColor(string style, bool IsSecondary = false)
  147.         {
  148.             if (IsSecondary)
  149.                 return FG_SECONDARY;
  150.  
  151.             Color newColor = FG_PRIMARYLIGHT;
  152.  
  153.             if (style != null && style == "dark")
  154.                 newColor = FG_PRIMARYDARK;
  155.  
  156.             return newColor;
  157.         }
  158.  
  159.         public bool OnTouch(View v, MotionEvent e)
  160.         {
  161.             var activity = (MainActivity)Context;
  162.             KeyboardPopupRowView popup = activity.kPopup;
  163.  
  164.             // capture position data
  165.             int x = (int)e.GetX();
  166.             int y = (int)e.GetY();
  167.  
  168.             switch (e.Action)
  169.             {
  170.                 case MotionEventActions.Down:
  171.                     activity.Debug("[TOUCH] Down \"" + key.Primary.Id + "\"");
  172.  
  173.                     // track the length of the down event to simulate a long touch
  174.                     TrackLongPress();          
  175.  
  176.                     int parentIndex = ((KeyboardView)v.Parent.Parent).IndexOfChild((View)v.Parent);
  177.                     int topOffset = keyboard.keyMargin + (parentIndex * keyboard.keyHeight);
  178.                     if (!key.SuppressPopup)
  179.                         popup.Show(v.Left, v.Top + topOffset, key);
  180.                     break;
  181.                 case MotionEventActions.Move:
  182.                     activity.Debug("[TOUCH] Move \"" + key.Primary.Id + "\" [" + x + ", " + y + "]");
  183.  
  184.                     // check key bounds
  185.                     int leftBound = -keyboard.keyMargin - popup.offsetX;
  186.                     if (x < leftBound || y > keyboard.keyHeight || x > (popup.ChildCount * keyboard.keyWidth))
  187.                     {
  188.                         popup.Hide();
  189.                         return true;
  190.                     }
  191.  
  192.                     bool popupHidden = popup.IsHidden();
  193.                     if (!popupHidden && y < 0 && y > -(keyboard.keyHeight + keyboard.keyMargin))
  194.                     {
  195.                         popup.Highlight(x);
  196.                     }
  197.                     break;
  198.                 case MotionEventActions.Up:
  199.                     activity.Debug("[TOUCH] Up \"" + key.Primary.Id + "\"");
  200.  
  201.                     isDown = false;
  202.  
  203.                     // short circuit the up if we've supershifted so we don't shift again
  204.                     if (keyboard.hasSuperShifted)
  205.                     {
  206.                         keyboard.hasSuperShifted = false;
  207.                         return true;
  208.                     }
  209.  
  210.                     if (popup.activeKey != null)
  211.                         popup.activeKey.KeyUp();
  212.                     else
  213.                         KeyUp(keyboard.swapped);
  214.  
  215.                     popup.Hide();
  216.  
  217.                     // haptic feedback
  218.                     PerformHapticFeedback(FeedbackConstants.KeyboardTap);
  219.                        
  220.                     break;
  221.                 default:
  222.                     return false;
  223.             }
  224.  
  225.             return true;
  226.         }
  227.  
  228.         public void TrackLongPress()
  229.         {
  230.             if (key.Primary.Id == "shift")
  231.             {
  232.                 isDown = true;
  233.                 ThreadPool.QueueUserWorkItem(o =>
  234.                 {
  235.                     Thread.Sleep(LongTouchDelay);
  236.                     ((MainActivity)Context).RunOnUiThread(() =>
  237.                     {
  238.                         if (isDown)
  239.                             keyboard.SuperShift();
  240.                     });
  241.                 });
  242.             }
  243.  
  244.             if (key.Primary.Id == "backspace")
  245.             {
  246.                 isDown = true;
  247.                 ThreadPool.QueueUserWorkItem(o =>
  248.                 {
  249.                     BackspaceWait(true);
  250.                 });
  251.             }
  252.  
  253.             return;
  254.         }
  255.  
  256.         public async void BackspaceWait(bool first = false)
  257.         {
  258.             int delay = first ? LongTouchDelay : ShortTouchDelay;
  259.             Thread.Sleep(delay);
  260.            
  261.             if (isDown)
  262.             {
  263.                 keyboard.Backspace();
  264.                 BackspaceWait();
  265.             }            
  266.         }
  267.  
  268.         // key was pressed
  269.         public virtual void KeyUp(bool secondary = false)
  270.         {
  271.             KeyState ks = secondary && key.Secondary != null ? key.Secondary : key.Primary;
  272.  
  273.             ((MainActivity)Context).Debug("[KEYUP] \"" + ks.Id + "\"");
  274.  
  275.             switch (ks.Id)
  276.             {
  277.                 case "swap":
  278.                     keyboard.Swap();
  279.                     break;
  280.                 case "shift":
  281.                     keyboard.Shift();
  282.                     break;
  283.                 case "num":
  284.                     keyboard.LoadKeyboard(KeyboardType.MATH_SMALL);
  285.                     break;
  286.                 case "abc":
  287.                     keyboard.LoadKeyboard(KeyboardType.QWERTY);
  288.                     break;
  289.                 case "backspace":
  290.                     keyboard.Backspace();
  291.                     break;
  292.                 default:
  293.                     keyboard.InsertKey(ks);
  294.                     break;
  295.             }
  296.         }
  297.     }
  298. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement