张高兴的 Xamarin.Forms 开发笔记:Android 快捷方式 Shortcut 应用

简介: 一、Shortcut 简介Shortcut 是 Android 7.1 (API Level 25) 的新特性,类似于苹果的 3D Touch ,但并不是压力感应,只是一种长按菜单。Shortcut 是受启动器限制的,也就是说国内大厂的定制系统大多数是不支持的,那些所谓的可以 pin 在桌面上的应用功能的快捷启动图标本质上就是 Shortcut 。

一、Shortcut 简介

Shortcut 是 Android 7.1 (API Level 25) 的新特性,类似于苹果的 3D Touch ,但并不是压力感应,只是一种长按菜单。Shortcut 是受启动器限制的,也就是说国内大厂的定制系统大多数是不支持的,那些所谓的可以 pin 在桌面上的应用功能的快捷启动图标本质上就是 Shortcut 。

img_724ee2ae69f2862ba9077055b76b9878.png

二、Shortcut 在 Xamarin.Forms 中的实现分析

本文讨论的是动态 Shortcut 实现。

实现方式无非两种思路,一种 Native to Forms ,另一种 Forms to Native 。博主最开始考虑的是 Forms to Native ,但没成功。在设置 ShortcutInfo 时需要一个 Intent ,其中一个构造函数为

public Intent(Context packageContext, Type type);

看着很容易,只要传入一个 Content 以及 把对应的页面 typeof 一下即可,但会抛出异常。原因是传入的 Forms Page 类并不是 Java 的原生类型。查阅 Xamarin.Android 的相关文档发现,这个 Type 是必须继承 Activity 类的。那么,所有的 Forms 页面均不可传入,Forms to Native 这条路也就不能走了。

Native to Forms 呢?

既然是需要依赖 Activity 的,那就通过新建一个 Android Activity 去调用 Forms 页面。

三、代码实现

下面新建一个空的 Cross-Platform 项目 ShortcutDemo ,使用 Shared Project 共享代码。(GitHub:https://github.com/ZhangGaoxing/xamarin-forms-demo/tree/master/ShortcutDemo

修改 Shared Project

添加两个 ContentPage 用作测试。

img_3625710aab094156d6e282a227c5c658.png

修改 Xamarin.Android

添加两个活动,ShortcutContainerActivity.cs 与 FormsActivity.cs 。

ShortcutContainerActivity.cs

ShortcutContainerActivity.cs 用来作为展示 Forms 页面的跳板,因此将其继承的 Activity 改成 global::Xamarin.Forms.Platform.Android.FormsAppCompatActivity 。同时把 OnCreate 的代码改成如下所示

protected override void OnCreate(Bundle savedInstanceState)
{
    TabLayoutResource = Resource.Layout.Tabbar;
    ToolbarResource = Resource.Layout.Toolbar;

    base.OnCreate(savedInstanceState);

    global::Xamarin.Forms.Forms.Init(this, savedInstanceState);
   
    Intent intent = Intent;
    // 获取传进来的页面名称
    string pageName = intent.GetStringExtra("PageName");

    var app = new App();
    // 设置显示的页面
    switch (pageName)
    {
        case "Page1":
            app.MainPage = new ShortcutDemo.Views.Page1();
            break;
        case "Page2":
            app.MainPage = new ShortcutDemo.Views.Page2();
            break;
        default:
            break;
    }

    LoadApplication(app);
}

要注意的是,顶部的 Activity 特性标签要改动,除了 MainLauncher 要改为 false 以外,其他的全部要和 MainActivity.cs 里的一样,不然会抛出异常,可能是主题不统一的原因。

[Activity(Label = "ShortcutDemo", Icon = "@drawable/icon", Theme = "@style/MainTheme", MainLauncher = false, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation)]

FormsActivity.cs

FormsActivity.cs 作为正常启动应用的活动,只是将其从 MainActivity.cs 中剥离开来。代码如下:

[Activity(Label = "ShortcutDemo", Icon = "@drawable/icon", Theme = "@style/MainTheme", MainLauncher = false, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation)]
public class FormsActivity : global::Xamarin.Forms.Platform.Android.FormsAppCompatActivity
{
    protected override void OnCreate(Bundle savedInstanceState)
    {
        TabLayoutResource = Resource.Layout.Tabbar;
        ToolbarResource = Resource.Layout.Toolbar;

        base.OnCreate(savedInstanceState);

        global::Xamarin.Forms.Forms.Init(this, savedInstanceState);
        LoadApplication(new App());
    }
}

MainActivity.cs

MainActivity.cs 作为应用程序的入口,由于 Forms 的初始化以及加载已被剥离至 FormsActivity.cs 中,可将 MainActivity.cs 的继承改为 Activity 类。

  1. 在其中添加一个 SetShortcut() 方法用于设置 Shortcut 。首先添加一个 List 用于存放 ShortcutInfo,以备最后动态设置 Shortcut 作为参数传入。

    List<ShortcutInfo> shortcutInfoList = new List<ShortcutInfo>();
  2. 接下来实例化一个 Intent 。其中 SetClass 将跳板活动 ShortcutContainerActivity 传入;SetAction 是必须设置的,要不然报错都不知道怎么回事;PutExtra 用于向下一个活动传递参数,我们这里传入的名称用于在跳板活动里设置 MainPage 。

    Intent page1 = new Intent();
    page1.SetClass(this, typeof(ShortcutContainerActivity));
    page1.SetAction(Intent.ActionMain);
    page1.PutExtra("PageName", "Page1");
  3. 下面实例化 ShortcutInfo 。SetRank 为设置排序序号,最多显示5个 Shortcut ,也就是 0-4 ;SetIcon 为设置图标;SetShortLabel 与 SetLongLabel 则是设置长名称与段名称;SetIntent 则把上一步实例化的 Intent 传入;最后将其加入 List 。

    ShortcutInfo page1Info = new ShortcutInfo.Builder(this, "Page1")
    .SetRank(0)
    .SetIcon(Icon.CreateWithResource(this, Resource.Drawable.Page1))
    .SetShortLabel("Page1")
    .SetLongLabel("Page1")
    .SetIntent(page1)
    .Build();
    shortcutInfoList.Add(page1Info);
  4. 最后获取 ShortcutManager 进行动态设置 Shortcut

    ShortcutManager shortcutManager = (ShortcutManager)GetSystemService(Context.ShortcutService);
    shortcutManager.SetDynamicShortcuts(shortcutInfoList);

因此全部的 MainActivity.cs 的代码如下:

[Activity(Label = "ShortcutDemo", Icon = "@drawable/icon", Theme = "@style/MainTheme", MainLauncher = true, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation)]
public class MainActivity : Activity
{
    protected override void OnCreate(Bundle bundle)
    {
        base.OnCreate(bundle);

        SetShortcut();

        StartActivity(typeof(FormsActivity));
    }

    private void SetShortcut()
    {
        List<ShortcutInfo> shortcutInfoList = new List<ShortcutInfo>();

        Intent page1 = new Intent();
        page1.SetClass(this, typeof(ShortcutContainerActivity));
        page1.SetAction(Intent.ActionMain);
        page1.PutExtra("PageName", "Page1");
        ShortcutInfo page1Info = new ShortcutInfo.Builder(this, "Page1")
            .SetRank(0)
            .SetIcon(Icon.CreateWithResource(this, Resource.Drawable.Page1))
            .SetShortLabel("Page1")
            .SetLongLabel("Page1")
            .SetIntent(page1)
            .Build();
        shortcutInfoList.Add(page1Info);

        Intent page2 = new Intent();
        page2.SetClass(this, typeof(ShortcutContainerActivity));
        page2.SetAction(Intent.ActionMain);
        page2.PutExtra("PageName", "Page2");
        ShortcutInfo page2 = new ShortcutInfo.Builder(this, "Page2")
            .SetRank(1)
            .SetIcon(Icon.CreateWithResource(this, Resource.Drawable.Page2))
            .SetShortLabel("Page2")
            .SetLongLabel("Page2")
            .SetIntent(page2)
            .Build();
        shortcutInfoList.Add(page2);

        ShortcutManager shortcutManager = (ShortcutManager)GetSystemService(Context.ShortcutService);
        shortcutManager.SetDynamicShortcuts(shortcutInfoList);
    }
}

四、效果图

img_111260fc73f7ed0b8ea6e60d8b82c267.png

目录
相关文章
|
8月前
|
存储 Android开发
如何查看Flutter应用在Android设备上已被撤销的权限?
如何查看Flutter应用在Android设备上已被撤销的权限?
334 64
|
10月前
|
前端开发 Java Shell
【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
635 20
【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
|
10月前
|
Dart 前端开发 Android开发
【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
312 4
【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
|
12月前
|
JSON Java API
探索安卓开发:打造你的首个天气应用
在这篇技术指南中,我们将一起潜入安卓开发的海洋,学习如何从零开始构建一个简单的天气应用。通过这个实践项目,你将掌握安卓开发的核心概念、界面设计、网络编程以及数据解析等技能。无论你是初学者还是有一定基础的开发者,这篇文章都将为你提供一个清晰的路线图和实用的代码示例,帮助你在安卓开发的道路上迈出坚实的一步。让我们一起开始这段旅程,打造属于你自己的第一个安卓应用吧!
307 14
|
12月前
|
Java Linux 数据库
探索安卓开发:打造你的第一款应用
在数字时代的浪潮中,每个人都有机会成为创意的实现者。本文将带你走进安卓开发的奇妙世界,通过浅显易懂的语言和实际代码示例,引导你从零开始构建自己的第一款安卓应用。无论你是编程新手还是希望拓展技术的开发者,这篇文章都将为你打开一扇门,让你的创意和技术一起飞扬。
217 13
|
12月前
|
搜索推荐 前端开发 测试技术
打造个性化安卓应用:从设计到开发的全面指南
在这个数字时代,拥有一个定制的移动应用不仅是一种趋势,更是个人或企业品牌的重要延伸。本文将引导你通过一系列简单易懂的步骤,从构思你的应用理念开始,直至实现一个功能齐全的安卓应用。无论你是编程新手还是希望拓展技能的开发者,这篇文章都将为你提供必要的工具和知识,帮助你将创意转化为现实。
|
12月前
|
Java Android开发 开发者
探索安卓开发:构建你的第一个“Hello World”应用
在安卓开发的浩瀚海洋中,每个新手都渴望扬帆起航。本文将作为你的指南针,引领你通过创建一个简单的“Hello World”应用,迈出安卓开发的第一步。我们将一起搭建开发环境、了解基本概念,并编写第一行代码。就像印度圣雄甘地所说:“你必须成为你希望在世界上看到的改变。”让我们一起开始这段旅程,成为我们想要见到的开发者吧!
220 0
|
移动开发 安全 Android开发
构建高效Android应用:Kotlin协程的实践与优化策略
【5月更文挑战第30天】 在移动开发领域,性能优化始终是关键议题之一。特别是对于Android开发者来说,如何在保证应用流畅性的同时,提升代码的执行效率,已成为不断探索的主题。近年来,Kotlin语言凭借其简洁、安全和实用的特性,在Android开发中得到了广泛的应用。其中,Kotlin协程作为一种新的并发处理机制,为编写异步、非阻塞性的代码提供了强大工具。本文将深入探讨Kotlin协程在Android开发中的应用实践,以及如何通过协程优化应用性能,帮助开发者构建更高效的Android应用。
|
API 调度 Android开发
打造高效Android应用:探究Kotlin协程的优势与实践
【5月更文挑战第27天】在移动开发领域,性能优化和响应速度是衡量应用质量的关键因素。随着Kotlin语言的普及,协程作为其核心特性之一,为Android开发者提供了一种全新的并发处理方式。本文深入探讨了Kotlin协程在Android应用开发中的优势,并通过实例演示如何在实际项目中有效利用协程提升应用性能和用户体验。
|
移动开发 Android开发 开发者
构建高效Android应用:探究Kotlin协程的优势与实践
【5月更文挑战第21天】在移动开发领域,性能优化和流畅的用户体验是至关重要的。随着Kotlin语言在Android平台的广泛采纳,其并发处理的强大工具—协程(Coroutines),已成为提升应用响应性和效率的关键因素。本文将深入分析Kotlin协程的核心原理,探讨其在Android开发中的优势,并通过实例演示如何有效利用协程来优化应用性能,打造更加流畅的用户体验。
149 4

热门文章

最新文章