Browse Source

[DROID] Implemented Popups, fixed AppBuilder

pull/883/head
Nikita Tsukanov 10 years ago
parent
commit
8c6d8ae832
  1. 6
      samples/ControlCatalog.Android/ControlCatalog.Android.csproj
  2. 47
      src/Android/Avalonia.Android/ActivityTracker.cs
  3. 4
      src/Android/Avalonia.Android/AndroidPlatform.cs
  4. 26
      src/Android/Avalonia.Android/AppBuilder.cs
  5. 3
      src/Android/Avalonia.Android/Avalonia.Android.csproj
  6. 15
      src/Android/Avalonia.Android/AvaloniaActivity.cs
  7. 18
      src/Android/Avalonia.Android/AvaloniaView.cs
  8. 4
      src/Android/Avalonia.Android/Platform/SkiaPlatform/AndroidFramebuffer.cs
  9. 24
      src/Android/Avalonia.Android/Platform/SkiaPlatform/InvalidationAwareSurfaceView.cs
  10. 91
      src/Android/Avalonia.Android/Platform/SkiaPlatform/PopupImpl.cs
  11. 152
      src/Android/Avalonia.Android/Platform/SkiaPlatform/TopLevelImpl.cs
  12. 6
      src/Android/Avalonia.Android/Platform/Specific/Helpers/AndroidKeyboardEventsHelper.cs
  13. 10
      src/Android/Avalonia.Android/Platform/Specific/Helpers/AndroidTouchEventsHelper.cs
  14. 4
      src/Avalonia.Controls/AppBuilderBase.cs
  15. 3
      src/Avalonia.DotNetFrameworkRuntime/AppBuilder.cs
  16. 5
      src/Skia/Avalonia.Skia/BitmapImpl.cs

6
samples/ControlCatalog.Android/ControlCatalog.Android.csproj

@ -29,7 +29,7 @@
<WarningLevel>4</WarningLevel> <WarningLevel>4</WarningLevel>
<AndroidUseSharedRuntime>True</AndroidUseSharedRuntime> <AndroidUseSharedRuntime>True</AndroidUseSharedRuntime>
<AndroidLinkMode>None</AndroidLinkMode> <AndroidLinkMode>None</AndroidLinkMode>
<EmbedAssembliesIntoApk>False</EmbedAssembliesIntoApk> <EmbedAssembliesIntoApk>True</EmbedAssembliesIntoApk>
<BundleAssemblies>False</BundleAssemblies> <BundleAssemblies>False</BundleAssemblies>
<AndroidCreatePackagePerAbi>False</AndroidCreatePackagePerAbi> <AndroidCreatePackagePerAbi>False</AndroidCreatePackagePerAbi>
<AndroidSupportedAbis>armeabi;armeabi-v7a;x86</AndroidSupportedAbis> <AndroidSupportedAbis>armeabi;armeabi-v7a;x86</AndroidSupportedAbis>
@ -112,10 +112,6 @@
<Project>{7062ae20-5dcc-4442-9645-8195bdece63e}</Project> <Project>{7062ae20-5dcc-4442-9645-8195bdece63e}</Project>
<Name>Avalonia.Diagnostics</Name> <Name>Avalonia.Diagnostics</Name>
</ProjectReference> </ProjectReference>
<ProjectReference Include="..\..\src\Avalonia.DotNetFrameworkRuntime\Avalonia.DotNetFrameworkRuntime.csproj">
<Project>{4a1abb09-9047-4bd5-a4ad-a055e52c5ee0}</Project>
<Name>Avalonia.DotNetFrameworkRuntime</Name>
</ProjectReference>
<ProjectReference Include="..\..\src\Avalonia.HtmlRenderer\Avalonia.HtmlRenderer.csproj"> <ProjectReference Include="..\..\src\Avalonia.HtmlRenderer\Avalonia.HtmlRenderer.csproj">
<Project>{5fb2b005-0a7f-4dad-add4-3ed01444e63d}</Project> <Project>{5fb2b005-0a7f-4dad-add4-3ed01444e63d}</Project>
<Name>Avalonia.HtmlRenderer</Name> <Name>Avalonia.HtmlRenderer</Name>

47
src/Android/Avalonia.Android/ActivityTracker.cs

@ -0,0 +1,47 @@
using Android.App;
using Android.OS;
namespace Avalonia.Android
{
internal class ActivityTracker : Java.Lang.Object, global::Android.App.Application.IActivityLifecycleCallbacks
{
public static Activity Current { get; private set; }
public void OnActivityCreated(Activity activity, Bundle savedInstanceState)
{
Current = activity;
}
public void OnActivityDestroyed(Activity activity)
{
if (Current == activity)
Current = null;
}
public void OnActivityPaused(Activity activity)
{
if (Current == activity)
Current = null;
}
public void OnActivityResumed(Activity activity)
{
Current = activity;
}
public void OnActivitySaveInstanceState(Activity activity, Bundle outState)
{
Current = activity;
}
public void OnActivityStarted(Activity activity)
{
Current = activity;
}
public void OnActivityStopped(Activity activity)
{
if (Current == activity)
Current = null;
}
}
}

4
src/Android/Avalonia.Android/AndroidPlatform.cs

@ -62,6 +62,8 @@ namespace Avalonia.Android
.Bind<IAssetLoader>().ToConstant(new AssetLoader(app.GetType().Assembly)); .Bind<IAssetLoader>().ToConstant(new AssetLoader(app.GetType().Assembly));
SkiaPlatform.Initialize(); SkiaPlatform.Initialize();
((global::Android.App.Application) global::Android.App.Application.Context.ApplicationContext)
.RegisterActivityLifecycleCallbacks(new ActivityTracker());
} }
public IWindowImpl CreateWindow() public IWindowImpl CreateWindow()
@ -76,7 +78,7 @@ namespace Avalonia.Android
public IPopupImpl CreatePopup() public IPopupImpl CreatePopup()
{ {
throw new NotImplementedException(); return new PopupImpl();
} }
} }
} }

26
src/Android/Avalonia.Android/AppBuilder.cs

@ -0,0 +1,26 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Android.App;
using Android.Content;
using Android.OS;
using Android.Runtime;
using Android.Views;
using Android.Widget;
using Avalonia.Controls;
using Avalonia.Platform;
using Avalonia.Shared.PlatformSupport;
namespace Avalonia
{
public sealed class AppBuilder : AppBuilderBase<AppBuilder>
{
public AppBuilder() : base(new StandardRuntimePlatform(),
builder => StandardRuntimePlatformServices.Register(builder.Instance?.GetType()?.Assembly))
{
}
}
}

3
src/Android/Avalonia.Android/Avalonia.Android.csproj

@ -61,8 +61,10 @@
<Reference Include="System.Xml" /> <Reference Include="System.Xml" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<Compile Include="ActivityTracker.cs" />
<Compile Include="AndroidPlatform.cs" /> <Compile Include="AndroidPlatform.cs" />
<Compile Include="AndroidThreadingInterface.cs" /> <Compile Include="AndroidThreadingInterface.cs" />
<Compile Include="AppBuilder.cs" />
<Compile Include="AvaloniaActivity.cs" /> <Compile Include="AvaloniaActivity.cs" />
<Compile Include="AvaloniaView.cs" /> <Compile Include="AvaloniaView.cs" />
<Compile Include="PlatformIconLoader.cs" /> <Compile Include="PlatformIconLoader.cs" />
@ -72,6 +74,7 @@
<Compile Include="Platform\Input\AndroidMouseDevice.cs" /> <Compile Include="Platform\Input\AndroidMouseDevice.cs" />
<Compile Include="Platform\SkiaPlatform\AndroidFramebuffer.cs" /> <Compile Include="Platform\SkiaPlatform\AndroidFramebuffer.cs" />
<Compile Include="Platform\SkiaPlatform\InvalidationAwareSurfaceView.cs" /> <Compile Include="Platform\SkiaPlatform\InvalidationAwareSurfaceView.cs" />
<Compile Include="Platform\SkiaPlatform\PopupImpl.cs" />
<Compile Include="Platform\SkiaPlatform\TopLevelImpl.cs" /> <Compile Include="Platform\SkiaPlatform\TopLevelImpl.cs" />
<Compile Include="Platform\Specific\IAndroidView.cs" /> <Compile Include="Platform\Specific\IAndroidView.cs" />
<Compile Include="Platform\Specific\Helpers\AndroidTouchEventsHelper.cs" /> <Compile Include="Platform\Specific\Helpers\AndroidTouchEventsHelper.cs" />

15
src/Android/Avalonia.Android/AvaloniaActivity.cs

@ -14,16 +14,17 @@ namespace Avalonia.Android
{ {
public abstract class AvaloniaActivity : Activity public abstract class AvaloniaActivity : Activity
{ {
AvaloniaView _view;
internal AvaloniaView View;
object _content; object _content;
protected override void OnCreate(Bundle savedInstanceState) protected override void OnCreate(Bundle savedInstanceState)
{ {
RequestWindowFeature(WindowFeatures.NoTitle); RequestWindowFeature(WindowFeatures.NoTitle);
_view = new AvaloniaView(this); View = new AvaloniaView(this);
if(_content != null) if(_content != null)
_view.Content = _content; View.Content = _content;
SetContentView(_view); SetContentView(View);
TakeKeyEvents(true); TakeKeyEvents(true);
base.OnCreate(savedInstanceState); base.OnCreate(savedInstanceState);
} }
@ -37,14 +38,14 @@ namespace Avalonia.Android
set set
{ {
_content = value; _content = value;
if (_view != null) if (View != null)
_view.Content = value; View.Content = value;
} }
} }
public override bool DispatchKeyEvent(KeyEvent e) public override bool DispatchKeyEvent(KeyEvent e)
{ {
return _view.DispatchKeyEvent(e); return View.DispatchKeyEvent(e);
} }
} }
} }

18
src/Android/Avalonia.Android/AvaloniaView.cs

@ -10,6 +10,7 @@ using Android.Runtime;
using Android.Views; using Android.Views;
using Android.Widget; using Android.Widget;
using Avalonia.Android.Platform.SkiaPlatform; using Avalonia.Android.Platform.SkiaPlatform;
using Avalonia.Controls;
using Avalonia.Controls.Embedding; using Avalonia.Controls.Embedding;
using Avalonia.Platform; using Avalonia.Platform;
@ -23,7 +24,7 @@ namespace Avalonia.Android
public AvaloniaView(Context context) : base(context) public AvaloniaView(Context context) : base(context)
{ {
_view = new ViewImpl(context); _view = new ViewImpl(context);
AddView(_view); AddView(_view.View);
_root = new EmbeddableControlRoot(_view); _root = new EmbeddableControlRoot(_view);
_root.Prepare(); _root.Prepare();
} }
@ -36,7 +37,7 @@ namespace Avalonia.Android
public override bool DispatchKeyEvent(KeyEvent e) public override bool DispatchKeyEvent(KeyEvent e)
{ {
return _view.DispatchKeyEvent(e); return _view.View.DispatchKeyEvent(e);
} }
class ViewImpl : TopLevelImpl, IEmbeddableWindowImpl class ViewImpl : TopLevelImpl, IEmbeddableWindowImpl
@ -45,8 +46,8 @@ namespace Avalonia.Android
public ViewImpl(Context context) : base(context) public ViewImpl(Context context) : base(context)
{ {
Focusable = true; View.Focusable = true;
FocusChange += ViewImpl_FocusChange; View.FocusChange += ViewImpl_FocusChange;
} }
private void ViewImpl_FocusChange(object sender, FocusChangeEventArgs e) private void ViewImpl_FocusChange(object sender, FocusChangeEventArgs e)
@ -54,6 +55,15 @@ namespace Avalonia.Android
if(!e.HasFocus) if(!e.HasFocus)
LostFocus?.Invoke(); LostFocus?.Invoke();
} }
protected override void OnResized(Size size)
{
MaxClientSize = size;
base.OnResized(size);
}
public WindowState WindowState { get; set; }
public IDisposable ShowDialog() => null;
} }
} }
} }

4
src/Android/Avalonia.Android/Platform/SkiaPlatform/AndroidFramebuffer.cs

@ -12,7 +12,11 @@ namespace Avalonia.Android.Platform.SkiaPlatform
public AndroidFramebuffer(Surface surface) public AndroidFramebuffer(Surface surface)
{ {
if(surface == null)
throw new ArgumentNullException(nameof(surface));
_window = ANativeWindow_fromSurface(JNIEnv.Handle, surface.Handle); _window = ANativeWindow_fromSurface(JNIEnv.Handle, surface.Handle);
if (_window == IntPtr.Zero)
throw new Exception("Unable to obtain ANativeWindow");
ANativeWindow_Buffer buffer; ANativeWindow_Buffer buffer;
var rc = new ARect() var rc = new ARect()
{ {

24
src/Android/Avalonia.Android/Platform/SkiaPlatform/InvalidationAwareSurfaceView.cs

@ -18,14 +18,13 @@ namespace Avalonia.Android
{ {
public abstract class InvalidationAwareSurfaceView : SurfaceView, ISurfaceHolderCallback, IPlatformHandle public abstract class InvalidationAwareSurfaceView : SurfaceView, ISurfaceHolderCallback, IPlatformHandle
{ {
private readonly Context _context;
bool _invalidateQueued; bool _invalidateQueued;
readonly object _lock = new object(); readonly object _lock = new object();
private readonly Handler _handler; private readonly Handler _handler;
public InvalidationAwareSurfaceView(Context context) : base(context) public InvalidationAwareSurfaceView(Context context) : base(context)
{ {
_context = context;
Holder.AddCallback(this); Holder.AddCallback(this);
_handler = new Handler(context.MainLooper); _handler = new Handler(context.MainLooper);
} }
@ -38,13 +37,11 @@ namespace Avalonia.Android
return; return;
_handler.Post(() => _handler.Post(() =>
{ {
lock (_lock) if (Holder.Surface?.IsValid != true)
{ return;
_invalidateQueued = false;
}
try try
{ {
Draw(); DoDraw();
} }
catch (Exception e) catch (Exception e)
{ {
@ -67,20 +64,29 @@ namespace Avalonia.Android
public void SurfaceChanged(ISurfaceHolder holder, Format format, int width, int height) public void SurfaceChanged(ISurfaceHolder holder, Format format, int width, int height)
{ {
Log.Info("AVALONIA", "Surface Changed"); Log.Info("AVALONIA", "Surface Changed");
Draw(); DoDraw();
} }
public void SurfaceCreated(ISurfaceHolder holder) public void SurfaceCreated(ISurfaceHolder holder)
{ {
Log.Info("AVALONIA", "Surface Created"); Log.Info("AVALONIA", "Surface Created");
Draw(); DoDraw();
} }
public void SurfaceDestroyed(ISurfaceHolder holder) public void SurfaceDestroyed(ISurfaceHolder holder)
{ {
Log.Info("AVALONIA", "Surface Destroyed"); Log.Info("AVALONIA", "Surface Destroyed");
} }
protected void DoDraw()
{
lock (_lock)
{
_invalidateQueued = false;
}
Draw();
}
protected abstract void Draw(); protected abstract void Draw();
public string HandleDescriptor => "SurfaceView"; public string HandleDescriptor => "SurfaceView";
} }

91
src/Android/Avalonia.Android/Platform/SkiaPlatform/PopupImpl.cs

@ -0,0 +1,91 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Android.App;
using Android.Content;
using Android.Graphics;
using Android.OS;
using Android.Runtime;
using Android.Views;
using Android.Widget;
using Avalonia.Platform;
namespace Avalonia.Android.Platform.SkiaPlatform
{
class PopupImpl : TopLevelImpl, IPopupImpl
{
private Point _position;
private bool _isAdded;
public PopupImpl() : base(ActivityTracker.Current, true)
{
}
private Size _clientSize = new Size(1, 1);
public override Size ClientSize
{
get { return base.ClientSize; }
set
{
if(View == null)
return;
_clientSize = value;
UpdateParams();
}
}
public override Point Position
{
get { return _position; }
set
{
_position = value;
PositionChanged?.Invoke(_position);
UpdateParams();
}
}
WindowManagerLayoutParams CreateParams() => new WindowManagerLayoutParams(0,
WindowManagerFlags.NotTouchModal, Format.Translucent)
{
Gravity = GravityFlags.Left | GravityFlags.Top,
WindowAnimations = 0,
X = (int) _position.X,
Y = (int) _position.Y,
Width = Math.Max(1, (int) _clientSize.Width),
Height = Math.Max(1, (int) _clientSize.Height)
};
void UpdateParams()
{
if (_isAdded)
ActivityTracker.Current?.WindowManager?.UpdateViewLayout(View, CreateParams());
}
public override void Show()
{
if (_isAdded)
return;
ActivityTracker.Current.WindowManager.AddView(View, CreateParams());
_isAdded = true;
}
public override void Hide()
{
if (_isAdded)
{
var wm = View.Context.ApplicationContext.GetSystemService(Context.WindowService)
.JavaCast<IWindowManager>();
wm.RemoveView(View);
_isAdded = false;
}
}
public override void Dispose()
{
Hide();
base.Dispose();
}
}
}

152
src/Android/Avalonia.Android/Platform/SkiaPlatform/TopLevelImpl.cs

@ -9,42 +9,32 @@ using Avalonia.Input.Raw;
using Avalonia.Platform; using Avalonia.Platform;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Reactive.Disposables;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Controls.Platform.Surfaces; using Avalonia.Controls.Platform.Surfaces;
namespace Avalonia.Android.Platform.SkiaPlatform namespace Avalonia.Android.Platform.SkiaPlatform
{ {
class TopLevelImpl : InvalidationAwareSurfaceView, IAndroidView, ITopLevelImpl, class TopLevelImpl : IAndroidView, ITopLevelImpl, IFramebufferPlatformSurface
ISurfaceHolderCallback, IFramebufferPlatformSurface
{ {
protected AndroidKeyboardEventsHelper<TopLevelImpl> _keyboardHelper; private readonly AndroidKeyboardEventsHelper<TopLevelImpl> _keyboardHelper;
private readonly AndroidTouchEventsHelper<TopLevelImpl> _touchHelper;
private ViewImpl _view;
private AndroidTouchEventsHelper<TopLevelImpl> _touchHelper; public TopLevelImpl(Context context, bool placeOnTop = false)
public TopLevelImpl(Context context) : base(context)
{ {
_view = new ViewImpl(context, this, placeOnTop);
_keyboardHelper = new AndroidKeyboardEventsHelper<TopLevelImpl>(this); _keyboardHelper = new AndroidKeyboardEventsHelper<TopLevelImpl>(this);
_touchHelper = new AndroidTouchEventsHelper<TopLevelImpl>(this, () => InputRoot, p => GetAvaloniaPointFromEvent(p)); _touchHelper = new AndroidTouchEventsHelper<TopLevelImpl>(this, () => InputRoot,
p => GetAvaloniaPointFromEvent(p));
MaxClientSize = new Size(Resources.DisplayMetrics.WidthPixels, Resources.DisplayMetrics.HeightPixels); MaxClientSize = new Size(_view.Resources.DisplayMetrics.WidthPixels,
ClientSize = MaxClientSize; _view.Resources.DisplayMetrics.HeightPixels);
} }
void ISurfaceHolderCallback.SurfaceChanged(ISurfaceHolder holder, Format format, int width, int height)
{
var newSize = new Size(width, height);
if (newSize != ClientSize)
{
MaxClientSize = newSize;
ClientSize = newSize;
Resized?.Invoke(ClientSize);
}
base.SurfaceChanged(holder, format, width, height);
}
private bool _handleEvents; private bool _handleEvents;
public bool HandleEvents public bool HandleEvents
@ -56,17 +46,24 @@ namespace Avalonia.Android.Platform.SkiaPlatform
_keyboardHelper.HandleEvents = _handleEvents; _keyboardHelper.HandleEvents = _handleEvents;
} }
} }
public WindowState WindowState
{
get { return WindowState.Normal; }
set { }
}
public virtual Point GetAvaloniaPointFromEvent(MotionEvent e) => new Point(e.GetX(), e.GetY()); public virtual Point GetAvaloniaPointFromEvent(MotionEvent e) => new Point(e.GetX(), e.GetY());
public IInputRoot InputRoot { get; private set; } public IInputRoot InputRoot { get; private set; }
public Size ClientSize { get; set; } public virtual Size ClientSize
{
get
{
if (_view == null)
return new Size(0, 0);
return new Size(_view.Width, _view.Height);
}
set
{
}
}
public Action Closed { get; set; } public Action Closed { get; set; }
@ -74,7 +71,7 @@ namespace Avalonia.Android.Platform.SkiaPlatform
public Action<RawInputEventArgs> Input { get; set; } public Action<RawInputEventArgs> Input { get; set; }
public Size MaxClientSize { get; private set; } public Size MaxClientSize { get; protected set; }
public Action<Rect> Paint { get; set; } public Action<Rect> Paint { get; set; }
@ -84,21 +81,21 @@ namespace Avalonia.Android.Platform.SkiaPlatform
public Action<Point> PositionChanged { get; set; } public Action<Point> PositionChanged { get; set; }
public View View => this; public View View => _view;
Action ITopLevelImpl.Activated { get; set; } Action ITopLevelImpl.Activated { get; set; }
IPlatformHandle ITopLevelImpl.Handle => this; IPlatformHandle ITopLevelImpl.Handle => _view;
public IEnumerable<object> Surfaces => new object[] { this }; public IEnumerable<object> Surfaces => new object[] {this};
public void Activate() public void Activate()
{ {
} }
public void Hide() public virtual void Hide()
{ {
this.Visibility = ViewStates.Invisible; _view.Visibility = ViewStates.Invisible;
} }
public void SetSystemDecorations(bool enabled) public void SetSystemDecorations(bool enabled)
@ -107,7 +104,7 @@ namespace Avalonia.Android.Platform.SkiaPlatform
public void Invalidate(Rect rect) public void Invalidate(Rect rect)
{ {
if (Holder?.Surface?.IsValid == true) base.Invalidate(); if (_view.Holder?.Surface?.IsValid == true) _view.Invalidate();
} }
public Point PointToClient(Point point) public Point PointToClient(Point point)
@ -134,9 +131,9 @@ namespace Avalonia.Android.Platform.SkiaPlatform
{ {
} }
public void Show() public virtual void Show()
{ {
this.Visibility = ViewStates.Visible; _view.Visibility = ViewStates.Visible;
} }
public void BeginMoveDrag() public void BeginMoveDrag()
@ -149,43 +146,80 @@ namespace Avalonia.Android.Platform.SkiaPlatform
//Not supported //Not supported
} }
public Point Position { get; set; } public virtual Point Position { get; set; }
public double Scaling => 1; public double Scaling => 1;
public IDisposable ShowDialog() void Draw()
{ {
throw new NotImplementedException(); Paint?.Invoke(new Rect(new Point(0, 0), ClientSize));
} }
public override bool DispatchTouchEvent(MotionEvent e) public void SetIcon(IWindowIconImpl icon)
{ {
bool callBase; // No window icons for mobile platforms
bool? result = _touchHelper.DispatchTouchEvent(e, out callBase);
bool baseResult = callBase ? base.DispatchTouchEvent(e) : false;
return result != null ? result.Value : baseResult;
} }
public override bool DispatchKeyEvent(KeyEvent e) public virtual void Dispose()
{ {
bool callBase; _view.Dispose();
bool? res = _keyboardHelper.DispatchKeyEvent(e, out callBase); _view = null;
bool baseResult = callBase ? base.DispatchKeyEvent(e) : false;
return res != null ? res.Value : baseResult;
} }
protected override void Draw() protected virtual void OnResized(Size size)
{ {
Paint?.Invoke(new Rect(new Point(0, 0), ClientSize)); Resized?.Invoke(size);
} }
public void SetIcon(IWindowIconImpl icon) class ViewImpl : InvalidationAwareSurfaceView, ISurfaceHolderCallback
{ {
// No window icons for mobile platforms private readonly TopLevelImpl _tl;
private Size _oldSize;
public ViewImpl(Context context, TopLevelImpl tl, bool placeOnTop) : base(context)
{
_tl = tl;
if (placeOnTop)
SetZOrderOnTop(true);
}
protected override void Draw()
{
_tl.Draw();
}
public override bool DispatchTouchEvent(MotionEvent e)
{
bool callBase;
bool? result = _tl._touchHelper.DispatchTouchEvent(e, out callBase);
bool baseResult = callBase ? base.DispatchTouchEvent(e) : false;
return result != null ? result.Value : baseResult;
}
public override bool DispatchKeyEvent(KeyEvent e)
{
bool callBase;
bool? res = _tl._keyboardHelper.DispatchKeyEvent(e, out callBase);
bool baseResult = callBase ? base.DispatchKeyEvent(e) : false;
return res != null ? res.Value : baseResult;
}
void ISurfaceHolderCallback.SurfaceChanged(ISurfaceHolder holder, Format format, int width, int height)
{
var newSize = new Size(width, height);
if (newSize != _oldSize)
{
_oldSize = newSize;
_tl.OnResized(newSize);
}
base.SurfaceChanged(holder, format, width, height);
}
} }
ILockedFramebuffer IFramebufferPlatformSurface.Lock()=>new AndroidFramebuffer(Holder.Surface); ILockedFramebuffer IFramebufferPlatformSurface.Lock()=>new AndroidFramebuffer(_view.Holder.Surface);
} }
} }

6
src/Android/Avalonia.Android/Platform/Specific/Helpers/AndroidKeyboardEventsHelper.cs

@ -12,7 +12,7 @@ using System.ComponentModel;
namespace Avalonia.Android.Platform.Specific.Helpers namespace Avalonia.Android.Platform.Specific.Helpers
{ {
public class AndroidKeyboardEventsHelper<TView> : IDisposable where TView : View, ITopLevelImpl, IAndroidView public class AndroidKeyboardEventsHelper<TView> : IDisposable where TView :ITopLevelImpl, IAndroidView
{ {
private TView _view; private TView _view;
private IInputElement _lastFocusedElement; private IInputElement _lastFocusedElement;
@ -90,7 +90,7 @@ namespace Avalonia.Android.Platform.Specific.Helpers
private void TryShowHideKeyboard(IInputElement element, bool value) private void TryShowHideKeyboard(IInputElement element, bool value)
{ {
var input = _view.Context.GetSystemService(Context.InputMethodService).JavaCast<InputMethodManager>(); var input = _view.View.Context.GetSystemService(Context.InputMethodService).JavaCast<InputMethodManager>();
if (value) if (value)
{ {
@ -102,7 +102,7 @@ namespace Avalonia.Android.Platform.Specific.Helpers
else else
{ {
//hide keyboard //hide keyboard
input.HideSoftInputFromWindow(_view.WindowToken, HideSoftInputFlags.None); input.HideSoftInputFromWindow(_view.View.WindowToken, HideSoftInputFlags.None);
} }
} }

10
src/Android/Avalonia.Android/Platform/Specific/Helpers/AndroidTouchEventsHelper.cs

@ -8,7 +8,7 @@ using System;
namespace Avalonia.Android.Platform.Specific.Helpers namespace Avalonia.Android.Platform.Specific.Helpers
{ {
public class AndroidTouchEventsHelper<TView> : IDisposable where TView : View, ITopLevelImpl, IAndroidView public class AndroidTouchEventsHelper<TView> : IDisposable where TView : ITopLevelImpl, IAndroidView
{ {
private TView _view; private TView _view;
public bool HandleEvents { get; set; } public bool HandleEvents { get; set; }
@ -63,10 +63,10 @@ namespace Avalonia.Android.Platform.Specific.Helpers
//if point is in view otherwise it's possible avalonia not to find the proper window to dispatch the event //if point is in view otherwise it's possible avalonia not to find the proper window to dispatch the event
_point = _getPointFunc(e); _point = _getPointFunc(e);
double x = _view.GetX(); double x = _view.View.GetX();
double y = _view.GetY(); double y = _view.View.GetY();
double r = x + _view.Width; double r = x + _view.View.Width;
double b = y + _view.Height; double b = y + _view.View.Height;
if (x <= _point.X && r >= _point.X && y <= _point.Y && b >= _point.Y) if (x <= _point.X && r >= _point.X && y <= _point.Y && b >= _point.Y)
{ {

4
src/Avalonia.Controls/AppBuilderBase.cs

@ -60,10 +60,10 @@ namespace Avalonia.Controls
/// </summary> /// </summary>
public Action<TAppBuilder> BeforeStartCallback { get; private set; } = builder => { }; public Action<TAppBuilder> BeforeStartCallback { get; private set; } = builder => { };
protected AppBuilderBase(IRuntimePlatform platform, Action platformSevices) protected AppBuilderBase(IRuntimePlatform platform, Action<TAppBuilder> platformSevices)
{ {
RuntimePlatform = platform; RuntimePlatform = platform;
RuntimePlatformServicesInitializer = platformSevices; RuntimePlatformServicesInitializer = () => platformSevices((TAppBuilder)this);
} }
/// <summary> /// <summary>

3
src/Avalonia.DotNetFrameworkRuntime/AppBuilder.cs

@ -17,7 +17,8 @@ namespace Avalonia
/// Initializes a new instance of the <see cref="AppBuilder"/> class. /// Initializes a new instance of the <see cref="AppBuilder"/> class.
/// </summary> /// </summary>
public AppBuilder() public AppBuilder()
: base(new StandardRuntimePlatform(), () => StandardRuntimePlatformServices.Register()) : base(new StandardRuntimePlatform(),
builder => StandardRuntimePlatformServices.Register(builder.Instance?.GetType()?.Assembly))
{ {
} }

5
src/Skia/Avalonia.Skia/BitmapImpl.cs

@ -63,7 +63,10 @@ namespace Avalonia.Skia
private static SKSurface CreateSurface(SKBitmap bitmap) private static SKSurface CreateSurface(SKBitmap bitmap)
{ {
IntPtr length; IntPtr length;
return SKSurface.Create(bitmap.Info, bitmap.GetPixels(out length), bitmap.RowBytes); var rv = SKSurface.Create(bitmap.Info, bitmap.GetPixels(out length), bitmap.RowBytes);
if (rv == null)
throw new Exception("Unable to create Skia surface");
return rv;
} }
public BitmapDrawingContext(SKSurface surface) : base(surface.Canvas) public BitmapDrawingContext(SKSurface surface) : base(surface.Canvas)

Loading…
Cancel
Save