diff --git a/xwords4/android/XWords4/archive/R.java b/xwords4/android/XWords4/archive/R.java
index cdb1e8da8..6f6e83e17 100644
--- a/xwords4/android/XWords4/archive/R.java
+++ b/xwords4/android/XWords4/archive/R.java
@@ -5058,6 +5058,7 @@ XLATE-ME
*/
public static final int phone_label=0x7f050223;
+ public static final int phone_state_rationale=0x7f050359;
/** Don't warn, but simply force to skip turn (give 0 points)
when user attempts to play word not in the wordlist.
Don't warn, but simply force to skip turn (give 0 points)
@@ -5822,7 +5823,7 @@ XLATE-ME
*/
public static final int remote_undone=0x7f050226;
- public static final int remove_sms=0x7f050359;
+ public static final int remove_sms=0x7f05035a;
/** Change the name of this group to:
*/
public static final int rename_group_label=0x7f050273;
diff --git a/xwords4/android/XWords4/res/values/strings.xml b/xwords4/android/XWords4/res/values/strings.xml
index e8904e4e7..ab100cdc5 100644
--- a/xwords4/android/XWords4/res/values/strings.xml
+++ b/xwords4/android/XWords4/res/values/strings.xml
@@ -2725,6 +2725,13 @@
receive moves.\n\nYou can re-open it to be asked for permission
again. Or you can remove the SMS communication setting.
+ Crosswords wants to determine
+ whether your phone can send SMS \"data\" messages to give you the
+ option of playing that way. If you don\'t ever want to play via SMS,
+ e.g. because you pay for each message or have a Verizon phone, it\'s
+ safe to permanently deny permission.
+
+
Remove SMS
diff --git a/xwords4/android/XWords4/res_src/values-ba_CK/strings.xml b/xwords4/android/XWords4/res_src/values-ba_CK/strings.xml
index f176d12f5..cec1fde61 100644
--- a/xwords4/android/XWords4/res_src/values-ba_CK/strings.xml
+++ b/xwords4/android/XWords4/res_src/values-ba_CK/strings.xml
@@ -2326,5 +2326,11 @@
os. Uoy nac llits nepo eht ,emag tub ti yam ton eb elba ot dnes ro
eviecer sevom.\n\nUoy nac nepo-er ti ot eb deksa rof noissimrep
niaga. Ro uoy nac evomer eht SMS noitacinummoc gnittes.
+ Sdrowssorc stnaw ot enimreted
+ rehtehw ruoy enohp nac dnes SMS \"atad\" segassem ot evig uoy eht
+ noitpo fo gniyalp taht yaw. Fi uoy nod\'t reve tnaw ot yalp aiv ,SMs
+ e.g. esuaceb uoy yap rof hcae egassem ro evah a Nozirev ,enohp ti\'s
+ efas ot yltnenamrep yned noissimrep.
+
Evomer SMS
diff --git a/xwords4/android/XWords4/res_src/values-ca_PS/strings.xml b/xwords4/android/XWords4/res_src/values-ca_PS/strings.xml
index 58184d46b..7db47b6da 100644
--- a/xwords4/android/XWords4/res_src/values-ca_PS/strings.xml
+++ b/xwords4/android/XWords4/res_src/values-ca_PS/strings.xml
@@ -2326,5 +2326,11 @@
SO. YOU CAN STILL OPEN THE GAME, BUT IT MAY NOT BE ABLE TO SEND OR
RECEIVE MOVES.\n\nYOU CAN RE-OPEN IT TO BE ASKED FOR PERMISSION
AGAIN. OR YOU CAN REMOVE THE SMS COMMUNICATION SETTING.
+ CROSSWORDS WANTS TO DETERMINE
+ WHETHER YOUR PHONE CAN SEND SMS \"DATA\" MESSAGES TO GIVE YOU THE
+ OPTION OF PLAYING THAT WAY. IF YOU DON\'T EVER WANT TO PLAY VIA SMS,
+ E.G. BECAUSE YOU PAY FOR EACH MESSAGE OR HAVE A VERIZON PHONE, IT\'S
+ SAFE TO PERMANENTLY DENY PERMISSION.
+
REMOVE SMS
diff --git a/xwords4/android/XWords4/src/org/eehouse/android/xw4/BoardDelegate.java b/xwords4/android/XWords4/src/org/eehouse/android/xw4/BoardDelegate.java
index 19a4c40f8..b4af54e64 100644
--- a/xwords4/android/XWords4/src/org/eehouse/android/xw4/BoardDelegate.java
+++ b/xwords4/android/XWords4/src/org/eehouse/android/xw4/BoardDelegate.java
@@ -42,7 +42,12 @@ import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.TextView;
+import java.util.ArrayList;
+import java.util.Iterator;
import java.util.Map;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.Semaphore;
import junit.framework.Assert;
@@ -68,10 +73,6 @@ import org.eehouse.android.xw4.jni.UtilCtxtImpl;
import org.eehouse.android.xw4.jni.XwJNI.GamePtr;
import org.eehouse.android.xw4.jni.XwJNI;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.concurrent.Semaphore;
-
public class BoardDelegate extends DelegateBase
implements TransportProcs.TPMsgHandler, View.OnClickListener,
DwnldDelegate.DownloadFinishedListener,
@@ -405,8 +406,8 @@ public class BoardDelegate extends DelegateBase
if ( self.m_summary.hasRematchInfo() ) {
self.tryRematchInvites( true );
} else {
- self.showInviteChoicesThen( Action.LAUNCH_INVITE_ACTION,
- self.m_sentInfo );
+ self.callInviteChoices( Action.LAUNCH_INVITE_ACTION,
+ self.m_sentInfo, true );
}
} else {
self.askDropRelay();
@@ -714,6 +715,43 @@ public class BoardDelegate extends DelegateBase
}
}
+ // Invitations need to check phone state to decide whether to offer SMS
+ // invitation. Complexity (showRationale) boolean is to prevent infinite
+ // loop of showing the rationale over and over. Android will always tell
+ // us to show the rationale, but if we've done it already we need to go
+ // straight to asking for the permission.
+ private void callInviteChoices( final Action action,
+ final DBUtils.SentInvitesInfo info,
+ boolean showRationale )
+ {
+ Perms23.Builder builder =
+ new Perms23.Builder( Perms23.Perm.READ_PHONE_STATE );
+
+ if ( showRationale ) {
+ builder.setOnShowRationale( new Perms23.OnShowRationale() {
+ @Override
+ public void onShouldShowRationale( Set perms )
+ {
+ makeOkOnlyBuilder( R.string.phone_state_rationale )
+ .setAction( Action.RETRY_PHONE_STATE_ACTION )
+ .setParams( action, info )
+ .show();
+ }
+ } );
+ }
+
+ builder.asyncQuery( m_activity, new Perms23.PermCbck() {
+ @Override
+ public void onPermissionResult( Map perms )
+ {
+ // Do the work regardless of result; just won't have
+ // SMS option
+ showInviteChoicesThen( action, info );
+ }
+ });
+ }
+
@Override
public void orientationChanged()
{
@@ -1006,6 +1044,10 @@ public class BoardDelegate extends DelegateBase
}
}, 10 );
}
+ } else if ( Action.RETRY_PHONE_STATE_ACTION == action ) {
+ Action stateAction = (Action)params[0];
+ DBUtils.SentInvitesInfo info = (DBUtils.SentInvitesInfo)params[1];
+ callInviteChoices( stateAction, info, false );
} else if ( positive ) {
handled = true;
JNICmd cmd = JNICmd.CMD_NONE;
diff --git a/xwords4/android/XWords4/src/org/eehouse/android/xw4/DlgDelegate.java b/xwords4/android/XWords4/src/org/eehouse/android/xw4/DlgDelegate.java
index f3603b5fd..1b607eb50 100644
--- a/xwords4/android/XWords4/src/org/eehouse/android/xw4/DlgDelegate.java
+++ b/xwords4/android/XWords4/src/org/eehouse/android/xw4/DlgDelegate.java
@@ -93,6 +93,7 @@ public class DlgDelegate {
NFC_TO_SELF,
DROP_RELAY_ACTION,
DROP_SMS_ACTION,
+ RETRY_PHONE_STATE_ACTION,
// Dict Browser
FINISH_ACTION,
diff --git a/xwords4/android/XWords4/src/org/eehouse/android/xw4/Perms23.java b/xwords4/android/XWords4/src/org/eehouse/android/xw4/Perms23.java
index ed6203a2a..9e9c659b8 100644
--- a/xwords4/android/XWords4/src/org/eehouse/android/xw4/Perms23.java
+++ b/xwords4/android/XWords4/src/org/eehouse/android/xw4/Perms23.java
@@ -60,9 +60,13 @@ public class Perms23 {
public interface PermCbck {
void onPermissionResult( Map perms );
}
+ public interface OnShowRationale {
+ void onShouldShowRationale( Set perms );
+ }
public static class Builder {
private Set m_perms = new HashSet();
+ private OnShowRationale m_onShow;
public Builder(Set perms) {
m_perms.addAll( perms );
@@ -77,11 +81,18 @@ public class Perms23 {
return this;
}
+ public Builder setOnShowRationale( OnShowRationale onShow )
+ {
+ m_onShow = onShow;
+ return this;
+ }
+
public void asyncQuery( Activity activity, PermCbck cbck )
{
- DbgUtils.logd( TAG, "asyncQuery()" );
+ DbgUtils.logd( TAG, "asyncQuery(%s)", m_perms.toString() );
boolean haveAll = true;
boolean shouldShow = false;
+ Set needShow = new HashSet();
ArrayList askStrings = new ArrayList();
for ( Perm perm : m_perms ) {
@@ -90,22 +101,22 @@ public class Perms23 {
== ContextCompat.checkSelfPermission( activity, permStr );
// For research: ask the OS if we should be printing a rationale
- if ( BuildConfig.DEBUG && !haveIt ) {
- shouldShow = shouldShow || ActivityCompat
- .shouldShowRequestPermissionRationale( activity, permStr );
+ if ( !haveIt ) {
+ askStrings.add( permStr );
+
+ if ( ActivityCompat
+ .shouldShowRequestPermissionRationale( activity,
+ permStr ) ) {
+ needShow.add( perm );
+ }
}
haveAll = haveAll && haveIt;
- if ( !haveIt ) {
- askStrings.add( permStr );
- }
}
- if ( shouldShow ) {
- DbgUtils.showf( "Should show rationale!!!" );
- }
-
- if ( haveAll ) {
+ if ( 0 < needShow.size() && null != m_onShow ) {
+ m_onShow.onShouldShowRationale( needShow );
+ } else if ( haveAll ) {
Map map = new HashMap();
for ( Perm perm : m_perms ) {
map.put( perm, true );
@@ -117,7 +128,7 @@ public class Perms23 {
ActivityCompat.requestPermissions( activity, permsArray, code );
}
- DbgUtils.logd( TAG, "asyncQuery(%s) => %b", m_perms.toString(), haveAll );
+ DbgUtils.logd( TAG, "asyncQuery(%s) DONE", m_perms.toString() );
}
}