Test App for ImsService
A test application that tests the ImsService APIs.
Currently only used to test the integration of the
ImsRegistration APIs.
Bug: 63987047
Test: Install app
Change-Id: I54ea68887bc2ebbc17520a625d1f64e763cbf995
diff --git a/testapps/ImsTestService/Android.mk b/testapps/ImsTestService/Android.mk
new file mode 100644
index 0000000..6f73238
--- /dev/null
+++ b/testapps/ImsTestService/Android.mk
@@ -0,0 +1,24 @@
+LOCAL_PATH:= $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_STATIC_ANDROID_LIBRARIES := \
+ android-support-v4 \
+ android-support-v7-appcompat \
+ android-support-v7-recyclerview \
+ android-support-v7-cardview
+
+LOCAL_USE_AAPT2 := true
+
+src_dirs := src
+res_dirs := res
+
+LOCAL_SRC_FILES := $(call all-java-files-under, $(src_dirs))
+LOCAL_RESOURCE_DIR := $(addprefix $(LOCAL_PATH)/, $(res_dirs))
+
+LOCAL_PACKAGE_NAME := ImsTestApp
+
+LOCAL_CERTIFICATE := platform
+LOCAL_PRIVILEGED_MODULE := true
+
+include $(BUILD_PACKAGE)
diff --git a/testapps/ImsTestService/AndroidManifest.xml b/testapps/ImsTestService/AndroidManifest.xml
new file mode 100644
index 0000000..a0172eb
--- /dev/null
+++ b/testapps/ImsTestService/AndroidManifest.xml
@@ -0,0 +1,51 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ coreApp="true"
+ package="com.android.phone.testapps.imstestapp">
+ <application
+ android:label="ImsTestService"
+ android:directBootAware="true">
+ <activity
+ android:name=".ImsTestServiceApp"
+ android:label="ImsTestService">
+ <intent-filter>
+ <action android:name="android.intent.action.MAIN" />
+ <category android:name="android.intent.category.DEFAULT" />
+ <category android:name="android.intent.category.LAUNCHER" />
+ </intent-filter>
+ </activity>
+
+ <activity android:name=".ImsRegistrationActivity" android:label="IMS Registration" />
+ <activity android:name=".ImsCallingActivity" android:label="IMS Calling" />
+
+ <service android:name=".TestImsService"
+ android:exported="true"
+ android:enabled="true"
+ android:persistent="true"
+ android:permission="android.permission.BIND_IMS_SERVICE">
+ <meta-data android:name="android.telephony.ims.MMTEL_FEATURE" android:value="true"/>
+ <!--meta-data android:name="android.telephony.ims.EMERGENCY_MMTEL_FEATURE"
+ android:value="true" /-->
+ <intent-filter>
+ <action android:name="android.telephony.ims.ImsService" />
+ </intent-filter>
+ </service>
+ </application>
+</manifest>
+
diff --git a/testapps/ImsTestService/res/layout/activity_calling.xml b/testapps/ImsTestService/res/layout/activity_calling.xml
new file mode 100644
index 0000000..968dcf1
--- /dev/null
+++ b/testapps/ImsTestService/res/layout/activity_calling.xml
@@ -0,0 +1,60 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical"
+ android:paddingLeft="4dp">
+
+ <GridLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:columnCount="2" android:rowCount="2">
+
+ <CheckBox
+ android:id="@+id/call_cap_voice"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_column="0"
+ android:layout_gravity="center" android:layout_row="0"
+ android:text="@string/calling_cap_voice"/>
+ <CheckBox
+ android:id="@+id/call_cap_video"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_column="1"
+ android:layout_gravity="center" android:layout_row="0"
+ android:text="@string/calling_cap_video"/>
+ <CheckBox
+ android:id="@+id/call_cap_ut"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_column="0"
+ android:layout_gravity="center" android:layout_row="1"
+ android:text="@string/calling_cap_ut"/>
+ <CheckBox
+ android:id="@+id/call_cap_sms"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_column="1"
+ android:layout_gravity="center" android:layout_row="1"
+ android:text="@string/calling_cap_sms"/>
+ </GridLayout>
+ <Button
+ android:id="@+id/call_cap_change"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/calling_cap_change_button" />
+</LinearLayout>
\ No newline at end of file
diff --git a/testapps/ImsTestService/res/layout/activity_main.xml b/testapps/ImsTestService/res/layout/activity_main.xml
new file mode 100644
index 0000000..35c6ae2
--- /dev/null
+++ b/testapps/ImsTestService/res/layout/activity_main.xml
@@ -0,0 +1,98 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical"
+ android:paddingLeft="4dp">
+
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical" >
+
+ <TextView
+ android:id="@+id/features_main_text"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/features_main_text"/>
+ <CheckBox
+ android:id="@+id/features_check_mmtel"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/features_check_mmtel"/>
+ <CheckBox
+ android:id="@+id/features_check_rcs"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/features_check_rcs"/>
+ <Button
+ android:id="@+id/features_change_button"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:paddingRight="4dp"
+ android:text="@string/features_change_button"/>
+ </LinearLayout>
+
+ <View
+ android:layout_width="match_parent"
+ android:layout_height= "1dp"
+ android:paddingRight="4dp"
+ android:background="?android:attr/listDivider" />
+
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical" >
+ <TextView
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="ImsService Controls"/>
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical">
+
+ <Button
+ android:id="@+id/control_launch_reg"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:paddingRight="4dp"
+ android:text="Registration"/>
+ <Button
+ android:id="@+id/control_launch_calling"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:paddingRight="4dp"
+ android:text="Calling"/>
+ </LinearLayout>
+ </LinearLayout>
+
+ <View
+ android:layout_width="match_parent"
+ android:layout_height= "1dp"
+ android:paddingRight="4dp"
+ android:background="?android:attr/listDivider" />
+
+ <LinearLayout
+ android:orientation="vertical"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:id="@+id/connections_list"/>
+</LinearLayout>
\ No newline at end of file
diff --git a/testapps/ImsTestService/res/layout/activity_registration.xml b/testapps/ImsTestService/res/layout/activity_registration.xml
new file mode 100644
index 0000000..2e381eb
--- /dev/null
+++ b/testapps/ImsTestService/res/layout/activity_registration.xml
@@ -0,0 +1,78 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical"
+ android:paddingLeft="4dp">
+
+ <LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal"
+ android:paddingLeft="4dp">
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/reg_text_reg_tech"/>
+ <Spinner
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:id="@+id/reg_tech_selector"/>
+ </LinearLayout>
+ <Button
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/reg_registered_button"
+ android:id="@+id/reg_registered_button"/>
+ <Button
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/reg_registering_button"
+ android:id="@+id/reg_registering_button"/>
+
+ <View
+ android:layout_width="match_parent"
+ android:layout_height= "1dp"
+ android:paddingRight="4dp"
+ android:background="?android:attr/listDivider" />
+
+ <include layout="@layout/construct_imsreasoninfo"
+ android:id="@+id/deregistered_imsreasoninfo" />
+ <Button
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/reg_deregistered_button"
+ android:id="@+id/reg_deregistered_button"/>
+
+ <View
+ android:layout_width="match_parent"
+ android:layout_height= "1dp"
+ android:paddingRight="4dp"
+ android:background="?android:attr/listDivider" />
+
+ <include layout="@layout/construct_imsreasoninfo"
+ android:id="@+id/regchangefail_imsreasoninfo" />
+ <Button
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/reg_changefailed_button"
+ android:id="@+id/reg_changefailed_button"/>
+</LinearLayout>
\ No newline at end of file
diff --git a/testapps/ImsTestService/res/layout/construct_imsreasoninfo.xml b/testapps/ImsTestService/res/layout/construct_imsreasoninfo.xml
new file mode 100644
index 0000000..dd32ca3
--- /dev/null
+++ b/testapps/ImsTestService/res/layout/construct_imsreasoninfo.xml
@@ -0,0 +1,74 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical" >
+
+ <TextView
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/imsreasoninfo_text"/>
+
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal">
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_weight="0"
+ android:maxLines="1" android:minEms="2" android:paddingRight="4dp"
+ android:text="@string/imsreasoninfo_errorcode"/>
+ <EditText
+ android:id="@+id/imsreasoninfo_error"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_weight="1"
+ android:ems="3"
+ android:inputType="number" android:text="0"/>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_weight="0"
+ android:autoText="true" android:maxLines="1" android:paddingRight="4dp"
+ android:text="@string/imsreasoninfo_extracode"/>
+ <EditText
+ android:id="@+id/imsreasoninfo_extra"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_weight="1"
+ android:ems="3"
+ android:inputType="number" android:text="0"/>
+ </LinearLayout>
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:layout_weight="1" android:orientation="horizontal">
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" android:layout_weight="0"
+ android:paddingRight="4dp" android:text="@string/imsreasoninfo_message"/>
+ <EditText
+ android:id="@+id/imsreasoninfo_message"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_weight="1"
+ android:ems="10"
+ android:inputType="text"/>
+ </LinearLayout>
+
+</LinearLayout>
\ No newline at end of file
diff --git a/testapps/ImsTestService/res/layout/ims_connection.xml b/testapps/ImsTestService/res/layout/ims_connection.xml
new file mode 100644
index 0000000..4c08082
--- /dev/null
+++ b/testapps/ImsTestService/res/layout/ims_connection.xml
@@ -0,0 +1,44 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+<android.support.v7.widget.CardView
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:card_view="http://schemas.android.com/apk/res-auto"
+ android:layout_gravity="center"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:id="@+id/connection_info"
+ card_view:cardCornerRadius="4dp"
+ card_view:cardElevation="4dp"
+ card_view:cardUseCompatPadding="true">
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical" >
+ <TextView
+ android:id="@+id/reg_main_text"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" android:text="@string/features_main_text"/>
+ <CheckBox
+ android:id="@+id/reg_check_mmtel"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" android:text="@string/features_check_mmtel"/>
+ <CheckBox
+ android:id="@+id/reg_check_rcs"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" android:text="@string/features_check_rcs"/>
+ </LinearLayout>
+</android.support.v7.widget.CardView>
\ No newline at end of file
diff --git a/testapps/ImsTestService/res/values/donottranslate_strings.xml b/testapps/ImsTestService/res/values/donottranslate_strings.xml
new file mode 100644
index 0000000..e6db1b8
--- /dev/null
+++ b/testapps/ImsTestService/res/values/donottranslate_strings.xml
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ ~ Copyright (C) 2017 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<resources>
+ <string name="features_main_text">Registration Configuration</string>
+ <string name="features_check_mmtel">MmTel Feature</string>
+ <string name="features_check_rcs">RCS Feature</string>
+ <string name="features_change_button">Change Features</string>
+
+ <string name="reg_text_reg_tech">Registration Technology</string>
+ <string name="reg_registered_button">Send Registered</string>
+ <string name="reg_registering_button">Send Registering</string>
+ <string name="reg_deregistered_button">Send Deregistered Using Reason Above</string>
+ <string name="reg_changefailed_button">Reg Change Failed Using Reason Above</string>
+
+ <string name="imsreasoninfo_text">Construct ImsReasonInfo</string>
+ <string name="imsreasoninfo_errorcode">Error Code</string>
+ <string name="imsreasoninfo_extracode">Extra Code</string>
+ <string name="imsreasoninfo_message">Message</string>
+
+ <string name="calling_cap_voice">Voice</string>
+ <string name="calling_cap_video">Video</string>
+ <string name="calling_cap_ut">UT</string>
+ <string name="calling_cap_sms">SMS</string>
+ <string name="calling_cap_change_button">Change Capabilities</string>
+</resources>
\ No newline at end of file
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsCallingActivity.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsCallingActivity.java
new file mode 100644
index 0000000..d8d56fd
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsCallingActivity.java
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.app.Activity;
+import android.os.Bundle;
+import android.telephony.ims.internal.feature.MmTelFeature;
+import android.widget.Button;
+import android.widget.CheckBox;
+import android.widget.Toast;
+
+public class ImsCallingActivity extends Activity {
+
+ //Capabilities available by service
+ private CheckBox mCapVoiceAvailBox;
+ private CheckBox mCapVideoAvailBox;
+ private CheckBox mCapUtAvailBox;
+ private CheckBox mCapSmsAvailBox;
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ setContentView(R.layout.activity_calling);
+
+ TestMmTelFeatureImpl.getInstance().setContext(this);
+
+ mCapVoiceAvailBox = findViewById(R.id.call_cap_voice);
+ mCapVideoAvailBox = findViewById(R.id.call_cap_video);
+ mCapUtAvailBox = findViewById(R.id.call_cap_ut);
+ mCapSmsAvailBox = findViewById(R.id.call_cap_sms);
+ Button capChangedButton = findViewById(R.id.call_cap_change);
+ capChangedButton.setOnClickListener((v) -> onCapabilitiesChangedClicked());
+ }
+
+ private void onCapabilitiesChangedClicked() {
+ if (!isFrameworkConnected()) {
+ return;
+ }
+ boolean isVoiceAvail = mCapVoiceAvailBox.isChecked();
+ boolean isVideoAvail = mCapVideoAvailBox.isChecked();
+ boolean isUtAvail = mCapUtAvailBox.isChecked();
+ // Not used yet
+ boolean isSmsAvail = mCapSmsAvailBox.isChecked();
+
+ MmTelFeature.MmTelCapabilities capabilities = new MmTelFeature.MmTelCapabilities();
+ if (isVoiceAvail) {
+ capabilities.addCapabilities(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_VOICE);
+ }
+ if (isVideoAvail) {
+ capabilities.addCapabilities(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_VIDEO);
+ }
+ if (isUtAvail) {
+ capabilities.addCapabilities(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_UT);
+ }
+ TestMmTelFeatureImpl.getInstance().sendCapabilitiesUpdate(capabilities);
+ }
+
+ private boolean isFrameworkConnected() {
+ if (!TestMmTelFeatureImpl.getInstance().isReady()) {
+ Toast.makeText(this, "Connection to Framework Unavailable", Toast.LENGTH_SHORT).show();
+ return false;
+ }
+ return true;
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsRegistrationActivity.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsRegistrationActivity.java
new file mode 100644
index 0000000..6391e53
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsRegistrationActivity.java
@@ -0,0 +1,155 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.app.Activity;
+import android.os.Bundle;
+import android.telephony.ims.stub.ImsRegistrationImplBase;
+import android.util.ArrayMap;
+import android.view.View;
+import android.widget.AdapterView;
+import android.widget.ArrayAdapter;
+import android.widget.Button;
+import android.widget.EditText;
+import android.widget.Spinner;
+import android.widget.Toast;
+
+import com.android.ims.ImsReasonInfo;
+
+import java.util.Map;
+
+public class ImsRegistrationActivity extends Activity {
+
+ private int mSelectedRegTech = ImsRegistrationImplBase.REGISTRATION_TECH_LTE;
+
+ private static final Map<String, Integer> REG_TECH = new ArrayMap<>(2);
+ static {
+ REG_TECH.put("LTE", ImsRegistrationImplBase.REGISTRATION_TECH_LTE);
+ REG_TECH.put("IWLAN", ImsRegistrationImplBase.REGISTRATION_TECH_IWLAN);
+ }
+
+ private View mDeregisteredReason;
+ private View mRegChangeFailedReason;
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ setContentView(R.layout.activity_registration);
+
+ //Set up registration tech spinner
+ Spinner regTechDropDown = findViewById(R.id.reg_tech_selector);
+ regTechDropDown.setAdapter(new ArrayAdapter<>(this,
+ android.R.layout.simple_spinner_dropdown_item,
+ REG_TECH.keySet().toArray(new String[REG_TECH.size()])));
+ regTechDropDown.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
+
+ @Override
+ public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
+ onTechDropDownChanged((String) parent.getItemAtPosition(position));
+ }
+
+ @Override
+ public void onNothingSelected(AdapterView<?> parent) {
+ // Don't change selection
+ }
+ });
+
+ // Map buttons to onClick listeners
+ Button registeredButton = findViewById(R.id.reg_registered_button);
+ registeredButton.setOnClickListener((v)->onRegisteredClicked());
+ Button registeringButton = findViewById(R.id.reg_registering_button);
+ registeringButton.setOnClickListener((v)->onRegisteringClicked());
+ Button deregisteredButton = findViewById(R.id.reg_deregistered_button);
+ deregisteredButton.setOnClickListener((v)->onDeregisteredClicked());
+ Button regChangeFailedButton = findViewById(R.id.reg_changefailed_button);
+ regChangeFailedButton.setOnClickListener((v)->onRegChangeFailedClicked());
+
+ mDeregisteredReason = findViewById(R.id.deregistered_imsreasoninfo);
+ mRegChangeFailedReason = findViewById(R.id.regchangefail_imsreasoninfo);
+ }
+
+ private void onRegisteredClicked() {
+ if (!isFrameworkConnected()) {
+ return;
+ }
+ TestImsRegistrationImpl.getInstance().onRegistered(mSelectedRegTech);
+ }
+
+ private void onRegisteringClicked() {
+ if (!isFrameworkConnected()) {
+ return;
+ }
+ TestImsRegistrationImpl.getInstance().onRegistering(mSelectedRegTech);
+ }
+
+ private void onDeregisteredClicked() {
+ if (!isFrameworkConnected()) {
+ return;
+ }
+ TestImsRegistrationImpl.getInstance().onDeregistered(getReasonInfo(mDeregisteredReason));
+ }
+
+ private void onRegChangeFailedClicked() {
+ if (!isFrameworkConnected()) {
+ return;
+ }
+ TestImsRegistrationImpl.getInstance().onTechnologyChangeFailed(mSelectedRegTech,
+ getReasonInfo(mRegChangeFailedReason));
+ }
+
+ private void onTechDropDownChanged(String item) {
+ mSelectedRegTech = REG_TECH.get(item);
+ }
+
+ private ImsReasonInfo getReasonInfo(View reasonView) {
+ EditText errorCodeText = reasonView.findViewById(R.id.imsreasoninfo_error);
+ EditText extraCodeText = reasonView.findViewById(R.id.imsreasoninfo_extra);
+ EditText messageText = reasonView.findViewById(R.id.imsreasoninfo_message);
+
+ int errorCode = ImsReasonInfo.CODE_UNSPECIFIED;
+ try {
+ errorCode = Integer.parseInt(errorCodeText.getText().toString());
+ } catch (NumberFormatException e) {
+ Toast.makeText(this, "Couldn't parse reason, defaulting to Unspecified.",
+ Toast.LENGTH_SHORT).show();
+ }
+
+ int extraCode = ImsReasonInfo.CODE_UNSPECIFIED;
+ try {
+ extraCode = Integer.parseInt(extraCodeText.getText().toString());
+ } catch (NumberFormatException e) {
+ Toast.makeText(this, "Couldn't parse reason, defaulting to Unspecified.",
+ Toast.LENGTH_SHORT).show();
+ }
+
+ String message = messageText.getText().toString();
+
+ ImsReasonInfo result = new ImsReasonInfo(errorCode, extraCode, message);
+ Toast.makeText(this, "getReasonInfo: " + result, Toast.LENGTH_SHORT).show();
+ return result;
+ }
+
+ private boolean isFrameworkConnected() {
+ if (TestImsRegistrationImpl.getInstance() == null) {
+ Toast.makeText(this, "Connection to Framework Unavailable!",
+ Toast.LENGTH_LONG).show();
+ return false;
+ }
+ return true;
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsTestServiceApp.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsTestServiceApp.java
new file mode 100644
index 0000000..89c50e9
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/ImsTestServiceApp.java
@@ -0,0 +1,59 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.app.Activity;
+import android.content.Intent;
+import android.os.Bundle;
+import android.widget.Button;
+import android.widget.LinearLayout;
+
+/**
+ * Main activity for Test ImsService Application.
+ */
+
+public class ImsTestServiceApp extends Activity {
+
+ private LinearLayout mConnections;
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ setContentView(R.layout.activity_main);
+
+ ((Button) findViewById(R.id.control_launch_reg)).setOnClickListener(
+ (view) -> launchRegistrationActivity());
+
+ ((Button) findViewById(R.id.control_launch_calling)).setOnClickListener(
+ (view) -> launchCallingActivity());
+
+ // Adds Card view for testing
+ mConnections = findViewById(R.id.connections_list);
+ mConnections.addView(getLayoutInflater().inflate(R.layout.ims_connection, null, false));
+ }
+
+ private void launchRegistrationActivity() {
+ Intent intent = new Intent(this, ImsRegistrationActivity.class);
+ startActivity(intent);
+ }
+
+ private void launchCallingActivity() {
+ Intent intent = new Intent(this, ImsCallingActivity.class);
+ startActivity(intent);
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsConfigImpl.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsConfigImpl.java
new file mode 100644
index 0000000..0010af4
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsConfigImpl.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.os.RemoteException;
+import android.telephony.ims.stub.ImsConfigImplBase;
+
+import com.android.ims.ImsConfig;
+import com.android.ims.ImsConfigListener;
+
+public class TestImsConfigImpl extends ImsConfigImplBase {
+
+ @Override
+ public int getProvisionedValue(int item) throws RemoteException {
+ return ImsConfig.FeatureValueConstants.ON;
+ }
+
+ @Override
+ public String getProvisionedStringValue(int item) throws RemoteException {
+ return null;
+ }
+
+ @Override
+ public int setProvisionedValue(int item, int value) throws RemoteException {
+ return ImsConfig.OperationStatusConstants.SUCCESS;
+ }
+
+ @Override
+ public int setProvisionedStringValue(int item, String value) throws RemoteException {
+ return ImsConfig.OperationStatusConstants.SUCCESS;
+ }
+
+ @Override
+ public void getFeatureValue(int feature, int network, ImsConfigListener listener)
+ throws RemoteException {
+ listener.onGetFeatureResponse(feature, network, ImsConfig.FeatureValueConstants.ON,
+ ImsConfig.OperationStatusConstants.SUCCESS);
+ }
+
+ @Override
+ public void setFeatureValue(int feature, int network, int value, ImsConfigListener listener)
+ throws RemoteException {
+ listener.onSetFeatureResponse(feature, network, value,
+ ImsConfig.OperationStatusConstants.SUCCESS);
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsRegistrationImpl.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsRegistrationImpl.java
new file mode 100644
index 0000000..50bf5d4
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsRegistrationImpl.java
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.telephony.ims.stub.ImsRegistrationImplBase;
+
+public class TestImsRegistrationImpl extends ImsRegistrationImplBase {
+
+ private static TestImsRegistrationImpl sInstance;
+
+ public static TestImsRegistrationImpl getInstance() {
+ if (sInstance == null) {
+ sInstance = new TestImsRegistrationImpl();
+ }
+ return sInstance;
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsService.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsService.java
new file mode 100644
index 0000000..71357bd
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestImsService.java
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.telephony.ims.ImsService;
+import android.telephony.ims.feature.MMTelFeature;
+import android.telephony.ims.feature.RcsFeature;
+import android.telephony.ims.stub.ImsRegistrationImplBase;
+import android.util.Log;
+
+/**
+ * Creates a test ImsService, which is used for testing framework IMS.
+ */
+
+public class TestImsService extends ImsService {
+
+ public static final String LOG_TAG = "ImsTestApp";
+
+ public static TestImsService mInstance;
+
+ public TestImsRegistrationImpl mImsRegistration;
+ public TestMmTelFeatureImpl mTestMmTelFeature;
+ public TestRcsFeatureImpl mTestRcsFeature;
+
+ public static TestImsService getInstance() {
+ return mInstance;
+ }
+
+ @Override
+ public void onCreate() {
+ Log.i(LOG_TAG, "TestImsService: onCreate");
+ mImsRegistration = TestImsRegistrationImpl.getInstance();
+ mTestMmTelFeature = TestMmTelFeatureImpl.getInstance();
+ mTestRcsFeature = new TestRcsFeatureImpl();
+
+ mInstance = this;
+ }
+
+ @Override
+ public MMTelFeature onCreateEmergencyMMTelImsFeature(int slotId) {
+ Log.i(LOG_TAG, "TestImsService: onCreateEmergencyMMTelImsFeature");
+ return mTestMmTelFeature;
+ }
+
+ @Override
+ public MMTelFeature onCreateMMTelImsFeature(int slotId) {
+ Log.i(LOG_TAG, "TestImsService: onCreateMMTelImsFeature");
+ return mTestMmTelFeature;
+ }
+
+ @Override
+ public RcsFeature onCreateRcsFeature(int slotId) {
+ return mTestRcsFeature;
+ }
+
+ @Override
+ public ImsRegistrationImplBase getRegistration(int slotId) {
+ Log.i(LOG_TAG, "TestImsService: getRegistration");
+ return mImsRegistration;
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestMmTelFeatureImpl.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestMmTelFeatureImpl.java
new file mode 100644
index 0000000..b112485
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestMmTelFeatureImpl.java
@@ -0,0 +1,163 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.app.PendingIntent;
+import android.os.RemoteException;
+import android.telephony.ims.feature.MMTelFeature;
+import android.telephony.ims.internal.feature.MmTelFeature;
+import android.telephony.ims.stub.ImsRegistrationImplBase;
+import android.util.Log;
+import android.widget.Toast;
+
+import com.android.ims.ImsConfig;
+import com.android.ims.internal.IImsConfig;
+import com.android.ims.internal.IImsRegistrationListener;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+public class TestMmTelFeatureImpl extends MMTelFeature {
+
+ private final String[] mImsFeatureStrings = {"VoLTE", "ViLTE", "VoWiFi", "ViWiFi",
+ "UTLTE", "UTWiFi"};
+
+ public static TestMmTelFeatureImpl sTestMmTelFeatureImpl;
+ private boolean mIsReady = false;
+ private PendingIntent mIncomingCallIntent;
+ private List<IImsRegistrationListener> mRegistrationListeners = new ArrayList<>();
+ private TestImsConfigImpl mConfig = new TestImsConfigImpl();
+
+ public TestMmTelFeatureImpl() {
+ setFeatureState(STATE_READY);
+ }
+
+ public static TestMmTelFeatureImpl getInstance() {
+ if (sTestMmTelFeatureImpl == null) {
+ sTestMmTelFeatureImpl = new TestMmTelFeatureImpl();
+ }
+ return sTestMmTelFeatureImpl;
+ }
+
+ public boolean isReady() {
+ return mIsReady;
+ }
+
+ public void sendCapabilitiesUpdate(MmTelFeature.MmTelCapabilities c) {
+ // Size of ImsConfig.FeatureConstants
+ int[] enabledCapabilities = new int[6];
+ // Apparently means disabled...?
+ Arrays.fill(enabledCapabilities, ImsConfig.FeatureConstants.FEATURE_TYPE_UNKNOWN);
+ int[] disabledCapabilities = new int[6];
+ Arrays.fill(disabledCapabilities, ImsConfig.FeatureConstants.FEATURE_TYPE_UNKNOWN);
+ int radioTech = TestImsRegistrationImpl.getInstance().getConnectionType();
+ StringBuilder sb = new StringBuilder(120);
+ // populate enabledCapabilities
+ switch (radioTech) {
+ case ImsRegistrationImplBase.REGISTRATION_TECH_LTE: {
+ if (c.isCapable(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_VOICE)) {
+ // enabled means equal to its own integer value.
+ enabledCapabilities[ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_LTE] =
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_LTE;
+ sb.append(mImsFeatureStrings[
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_LTE]);
+ sb.append(" ");
+ }
+ if (c.isCapable(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_VIDEO)) {
+ enabledCapabilities[ImsConfig.FeatureConstants.FEATURE_TYPE_VIDEO_OVER_LTE] =
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VIDEO_OVER_LTE;
+ sb.append(mImsFeatureStrings[
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VIDEO_OVER_LTE]);
+ sb.append(" ");
+ }
+ if (c.isCapable(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_UT)) {
+ enabledCapabilities[ImsConfig.FeatureConstants.FEATURE_TYPE_UT_OVER_LTE] =
+ ImsConfig.FeatureConstants.FEATURE_TYPE_UT_OVER_LTE;
+ sb.append(mImsFeatureStrings[
+ ImsConfig.FeatureConstants.FEATURE_TYPE_UT_OVER_LTE]);
+ }
+ break;
+ }
+ case ImsRegistrationImplBase.REGISTRATION_TECH_IWLAN: {
+ if (c.isCapable(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_VOICE)) {
+ enabledCapabilities[ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_WIFI] =
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_WIFI;
+ sb.append(mImsFeatureStrings[
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_WIFI]);
+ sb.append(" ");
+ }
+ if (c.isCapable(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_VIDEO)) {
+ enabledCapabilities[ImsConfig.FeatureConstants.FEATURE_TYPE_VIDEO_OVER_WIFI] =
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VOICE_OVER_WIFI;
+ sb.append(mImsFeatureStrings[
+ ImsConfig.FeatureConstants.FEATURE_TYPE_VIDEO_OVER_WIFI]);
+ sb.append(" ");
+ }
+ if (c.isCapable(MmTelFeature.MmTelCapabilities.CAPABILITY_TYPE_UT)) {
+ enabledCapabilities[ImsConfig.FeatureConstants.FEATURE_TYPE_UT_OVER_WIFI] =
+ ImsConfig.FeatureConstants.FEATURE_TYPE_UT_OVER_WIFI;
+ sb.append(mImsFeatureStrings[
+ ImsConfig.FeatureConstants.FEATURE_TYPE_UT_OVER_WIFI]);
+ }
+ break;
+ }
+ }
+ // make disabledCapabilities the opposite of enabledCapabilities
+ for (int i = 0; i < enabledCapabilities.length; i++) {
+ if (enabledCapabilities[i] != i) {
+ disabledCapabilities[i] = i;
+ }
+ }
+ Toast.makeText(mContext, "Sending Capabilities:{" + sb.toString() + "}",
+ Toast.LENGTH_LONG).show();
+ mRegistrationListeners.forEach((l) -> {
+ try {
+ l.registrationFeatureCapabilityChanged(1 /*ImsServiceClass.MMTel*/,
+ enabledCapabilities,
+ disabledCapabilities);
+ } catch (RemoteException e) {
+ // ignore
+ }
+ });
+ }
+
+ @Override
+ public int startSession(PendingIntent incomingCallIntent, IImsRegistrationListener listener) {
+ Log.i(TestImsService.LOG_TAG,
+ "startSession Called: pi=" + incomingCallIntent + " listener: " + listener);
+ mIncomingCallIntent = incomingCallIntent;
+ mRegistrationListeners.add(listener);
+ return super.startSession(incomingCallIntent, listener);
+ }
+
+ @Override
+ public void addRegistrationListener(IImsRegistrationListener listener) {
+ Log.i(TestImsService.LOG_TAG, "addRegistrationListener: " + listener);
+ mRegistrationListeners.add(listener);
+ }
+
+ @Override
+ public IImsConfig getConfigInterface() {
+ return mConfig;
+ }
+
+ @Override
+ public void onFeatureReady() {
+ mIsReady = true;
+ }
+}
diff --git a/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestRcsFeatureImpl.java b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestRcsFeatureImpl.java
new file mode 100644
index 0000000..996a569
--- /dev/null
+++ b/testapps/ImsTestService/src/com/android/phone/testapps/imstestapp/TestRcsFeatureImpl.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.phone.testapps.imstestapp;
+
+import android.telephony.ims.feature.RcsFeature;
+
+public class TestRcsFeatureImpl extends RcsFeature {
+
+ private boolean mIsReady = false;
+
+
+ public boolean isReady() {
+ return mIsReady;
+ }
+
+ @Override
+ public void onFeatureReady() {
+ mIsReady = true;
+ }
+}