您的位置:首页 > 移动开发 > Android开发

【Android】Scheme详解

2015-11-15 18:46 435 查看
说到scheme之前一直很少接触,基本上没有使用过,最近项目中使用到了scheme,研究了一下,scheme是下data标签的一个属性,通过scheme以及action的设置可以进行页面的跳转。

当我们通过Intent启动一个Activity的时候,一般分为显式跳转和隐式跳转,而隐式跳转我们通过setAction方法就可以实现,但有时我们需要通过设置URi的方式来进行页面的跳转,隐式启动则是不明确指定启动哪个Activity或者Service,而是通过设置Action、Data、Category,让系统来筛选出合适的目标。

例如:拨打电话:

[code]Intent intent = new Intent(Intent.ACTION_DIAL,Uri.parse(“tel:10086”));
startActivity(intent);


系统接收到隐式启动请求后,会根据系统中各个Activity在AndroidManifest.xml文件中声明的来比较和判断是否匹配当前的Intent请求的。

一 . 现在模拟一个场景,点击首页MainActivity跳转到secondActivity,点击secondActivity跳转到MainActivity(通过uri的方式),在跳转到MainActivity的时候,通过配置scheme,来实现模拟首页按钮的点击效果,具体效果图如下:



1.首先在AndroidManifest.xml中为MainActivity配置跳转参数。

[code]<intent-filter>
    <action android:name="android.intent.action.VIEW" />
    <category android:name="android.intent.category.DEFAULT" />
    <category android:name="android.intent.category.BROWSABLE" />

    <data android:scheme="@string/scheme" />
</intent-filter>


2 . String.xml文件

[code]<string name="scheme">myscheme</string>


3.MainActivity.java

[code]public class MainActivity extends Activity
{
    private TextView textView;

    @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initView();
    }

    /**
     * 
     * <初始化组件>
     * <功能详细描述>
     * @see [类、类#方法、类#成员]
     */
    private void initView()
    {
        textView = (TextView)findViewById(R.id.main_to_jump);

        textView.setOnClickListener(new OnClickListener()
        {

            @Override
            public void onClick(View v)
            {
                // 显式跳转
                Intent intent = new Intent(MainActivity.this, SecondActivity.class);
                startActivity(intent);
            }
        });
    }

    @Override
    protected void onNewIntent(Intent intent)
    {
        super.onNewIntent(intent);
        if (null != intent)
        {
            handlerIntent(intent);
        }
    }

    /**
     * 
     * <处理uri数据,模拟点击>
     * <功能详细描述>
     * @param intent
     * @see [类、类#方法、类#成员]
     */
    private void handlerIntent(Intent intent)
    {
        if (null != intent && null != intent.getAction() && null != intent.getScheme() && intent.getScheme().equals(getResources().getString(R.string.scheme)))
        {
            Uri schemeUri = intent.getData();

            String schemID = schemeUri.getAuthority();

            // 模拟点击
            switch (schemID)
            {
                case Contants.PRODUCT:
                    Toast.makeText(MainActivity.this, "通过scheme--点击了[" + Contants.PRODUCT + "]", Toast.LENGTH_SHORT).show();
                    break;
                case Contants.PASSWORD:
                    Toast.makeText(MainActivity.this, "通过scheme--点击了[" + Contants.PASSWORD + "]", Toast.LENGTH_SHORT).show();
                    break;
                case Contants.SHARE:
                    Toast.makeText(MainActivity.this, "通过scheme--点击了[" + Contants.SHARE + "]", Toast.LENGTH_SHORT).show();
                    break;
                default:
                    break;
            }
        }
    }
}


备注:onNewIntent是在该实例已经存在的情况下,才会调用,关于这个请点击:Android:onNewIntent()触发机制及注意事项

4 . SecondActivity.java

[code]public class SecondActivity extends Activity
{
    private TextView textView;

    @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_second);

        initView();
    }

    private void initView()
    {
        textView = (TextView)findViewById(R.id.jump_to_main);
        textView.setOnClickListener(new OnClickListener()
        {

            @Override
            public void onClick(View v)
            {
                Intent intent = new Intent();
                intent.setAction(Contants.MAIN_ACTION);
                intent.setData(Uri.parse("myscheme://share"));
                startActivity(intent);
            }
        });
    }
}


上述代码,通过uri的方式实现了页面的跳转,在AndroidManifest.xml中设置了data属性,data代表数据源,是中最复杂的标签,因为不同的Activity支持的数据来源和类型多种多样,所以需要通过详细的data标签信息来指明。

Data的语法如下:

[code]Data的语法:
<data android:host="string"
      android:mimeType="string"
      android:path="string"
      android:pathPattern="string"
      android:pathPrefix="string"
      android:port="string"
      android:scheme="string" />

Uri的格式:scheme://host:port/path or pathPrefix or pathPattern

如果scheme没有指定,那其它的属性均无效;

如果host没有指定,那么port,path,pathPrefix,pathPattern均无效;

如果在manifest里这样写:<data android:scheme="something" android:host="project.example.com" />

那么Uri uri = Uri.parse("something://project.example.com"); 才可以匹配

再如:
<data android:scheme="something" android:host="project.example.com" android:port="80"/>
等同于这样写:
<data android:scheme="something"/>
<data android:host="project.example.com"/>
<data android:port="80"/>
那么Uri uri = Uri.parse("something://project.example.com:80"); 才可以匹配

可以有多个data,只需匹配其中一个即可
<activity android:name=".MyActivityTwo" android:label="@string/activityTwo">
<intent-filter>
             <action android:name="android.intent.action.leo"></action>
                <category android:name="android.intent.category.DEFAULT"></category>
                <data android:scheme="x-id"/>
                <data android:scheme="something"/>
</intent-filter>
</activity>

Intent in = new Intent();
in.setAction("android.intent.action.leo");
in.addCategory(Intent.CATEGORY_DEFAULT);            in.setData(Uri.parse("something:"));//或者用这个亦可in.setData(Uri.parse("x- id:"));           
startActivity(in);


参考资料:

1.android 再解Intent,通过配置Action和Data跳转

2.intent-filter 之 data 「scheme, host, port, mimeType, path, pathPrefix, pathPattern」

二 . 浏览器启动APP

1.首先需要在AndroidMainifest.xml中对你要启动的那个activity进行如下设置:

[code]       <activity
            android:name=".MainActivity"
            android:launchMode="singleTask"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
            <intent-filter>
                <action android:name="android.intent.action.VIEW" />

                <category android:name="android.intent.category.DEFAULT" />
                <category android:name="android.intent.category.BROWSABLE" />

                <data android:scheme="myscheme://" />
            </intent-filter>
        </activity>


2.浏览器打开如下html页,即可启动App。

[code]<a href="myscheme://">打开app</a>


3.浏览器打开App时,如何获取网页带过来的数据。

[code]<a href="myscheme://?arg0=0&arg1=1">打开app</a>


(1).假如你是通过浏览器打开这个网页的,那么获取数据的方式为:

[code]Uri uri = getIntent().getData();  

String test1= uri.getQueryParameter("arg0"); 
String test2= uri.getQueryParameter("arg1");


(2)如果使用webview访问该网页,获取数据的操作为:

[code]webView.setWebViewClient(new WebViewClient(){
  @Override
  public boolean shouldOverrideUrlLoading(WebView view, String url) {
          Uri uri=Uri.parse(url);
          if(uri.getScheme().equals("myscheme")){
              String arg0=uri.getQueryParameter("arg0");
              String arg1=uri.getQueryParameter("arg1"); 
          }else{
              view.loadUrl(url);
          }
         return true;
  }
});


参考资料:如何通过Html网页调用本地安卓app?
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: