Skip to content

Commit 479a03b

Browse files
[Amazon] StopConnect for UDC in Android tv-casting-app
Updated Android & iOS tv-casting-app to send stopConnect command when user exits UDC before confirming passcode Changes 1. ConnectionExampleFragment.java track if user confirmed passcode or not 2. ConnectionExampleFragment.java onDestroy() send stopConnect() if user has not confirmed passcode 3. MCConnectionExampleViewModel track if user confirmed passcode or not 4. MCConnectionExampleView trigger stopConnect when Connecting view dissapear Test 1. Manually verfied stopConnect works for normal UDC and commissioner generated passcode UDC 2. Manually verified alternating attempt of normal UDC and commissioner generated passcode UDC works 3. Manually verified stopConnect is not called in other states other than pending passcode confirmation
1 parent 2ca3a49 commit 479a03b

File tree

4 files changed

+63
-8
lines changed

4 files changed

+63
-8
lines changed

examples/tv-casting-app/android/App/app/src/main/java/com/matter/casting/ConnectionExampleFragment.java

+32-2
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,14 @@
4242

4343
/** A {@link Fragment} to Verify or establish a connection with a selected Casting Player. */
4444
public class ConnectionExampleFragment extends Fragment {
45+
enum ConnectionState {
46+
PENDING_PASSCODE_CONFIRMATION,
47+
CONNECTING,
48+
CONNECTED,
49+
FAILED,
50+
CANCELLED,
51+
}
52+
4553
private static final String TAG = ConnectionExampleFragment.class.getSimpleName();
4654
// Time (in sec) to keep the commissioning window open, if commissioning is required.
4755
// Must be >= 3 minutes.
@@ -58,6 +66,7 @@ public class ConnectionExampleFragment extends Fragment {
5866
private TextView commissionerDeclarationErrorTextView;
5967
private Button connectionFragmentNextButton;
6068
private AlertDialog passcodeDialog;
69+
private ConnectionState connection_state = ConnectionState.PENDING_PASSCODE_CONFIRMATION;
6170

6271
public ConnectionExampleFragment(
6372
CastingPlayer targetCastingPlayer, boolean useCommissionerGeneratedPasscode) {
@@ -171,6 +180,7 @@ public void handle(Void v) {
171180
getActivity()
172181
.runOnUiThread(
173182
() -> {
183+
connection_state = ConnectionState.CONNECTED;
174184
connectionFragmentStatusTextView.setText(
175185
"Successfully connected to Casting Player with device name: "
176186
+ targetCastingPlayer.getDeviceName()
@@ -188,6 +198,7 @@ public void handle(MatterError err) {
188198
getActivity()
189199
.runOnUiThread(
190200
() -> {
201+
connection_state = ConnectionState.FAILED;
191202
connectionFragmentStatusTextView.setText(
192203
"Casting Player connection failed due to: " + err + "\n\n");
193204
});
@@ -262,6 +273,21 @@ public void handle(CommissionerDeclaration cd) {
262273
});
263274
}
264275

276+
@Override
277+
public void onDestroy() {
278+
super.onDestroy();
279+
Log.i(TAG, "onDestroy(), connection_state: " + connection_state);
280+
281+
// Only stop connection if we are pending passcode confirmation
282+
// We cannot stop connection once continueConnecting() is called
283+
if (connection_state == ConnectionState.PENDING_PASSCODE_CONFIRMATION) {
284+
MatterError err = targetCastingPlayer.stopConnecting();
285+
if (err.hasError()) {
286+
Log.e(TAG, "Going back before connection finishes but stopConnecting() failed due to: " + err);
287+
}
288+
}
289+
}
290+
265291
private void displayPasscodeInputDialog(Context context) {
266292
AlertDialog.Builder builder = new AlertDialog.Builder(context);
267293

@@ -328,7 +354,9 @@ public void onClick(DialogInterface dialog, int which) {
328354

329355
MatterError err = targetCastingPlayer.continueConnecting();
330356

331-
if (err.hasError()) {
357+
if (!err.hasError()) {
358+
connection_state = ConnectionState.CONNECTING;
359+
} else {
332360
MatterError finalErr = err;
333361
getActivity()
334362
.runOnUiThread(
@@ -363,7 +391,9 @@ public void onClick(DialogInterface dialog, int which) {
363391
connectionFragmentStatusTextView.setText(
364392
"Connection attempt with Casting Player cancelled by the Casting Client/Commissionee user. \n\nRoute back to exit. \n\n");
365393
MatterError err = targetCastingPlayer.stopConnecting();
366-
if (err.hasError()) {
394+
if (!err.hasError()) {
395+
connection_state = ConnectionState.CANCELLED;
396+
} else {
367397
MatterError finalErr = err;
368398
getActivity()
369399
.runOnUiThread(

examples/tv-casting-app/darwin/TvCasting/TvCasting/MCConnectionExampleView.swift

+3
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,9 @@ struct MCConnectionExampleView: View {
8888
viewModel.connect(selectedCastingPlayer: self.selectedCastingPlayer, useCommissionerGeneratedPasscode: self.useCommissionerGeneratedPasscode)
8989
}
9090
})
91+
.onDisappear(perform: {
92+
viewModel.cancelConnectionAttempt(selectedCastingPlayer: self.selectedCastingPlayer)
93+
})
9194
}
9295
}
9396

examples/tv-casting-app/darwin/TvCasting/TvCasting/MCConnectionExampleViewModel.swift

+28-1
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,8 @@ class MCConnectionExampleViewModel: ObservableObject {
2525

2626
var passcodeAlertController: UIAlertController?
2727

28+
var pendingPasscodeConfirmation: Bool = true;
29+
2830
// VendorId of the MCEndpoint on the MCCastingPlayer that the MCCastingApp desires to interact with after connection
2931
let kDesiredEndpointVendorId: UInt16 = 65521;
3032

@@ -42,13 +44,33 @@ class MCConnectionExampleViewModel: ObservableObject {
4244

4345
@Published var errorCodeDescription: String?
4446

47+
func cancelConnectionAttempt(selectedCastingPlayer: MCCastingPlayer?) {
48+
DispatchQueue.main.async {
49+
// Only stop connection if we are pending passcode confirmation
50+
// We cannot stop connection once continueConnecting() is called
51+
if self.pendingPasscodeConfirmation {
52+
self.Log.info("MCConnectionExampleViewModel cancelConnect(). User navigating back from ConnectionView")
53+
let err = selectedCastingPlayer?.stopConnecting()
54+
if err == nil {
55+
self.pendingPasscodeConfirmation = false;
56+
self.connectionStatus = "User cancelled the connection attempt with CastingPlayer.stopConnecting()."
57+
self.Log.info("MCConnectionExampleViewModel cancelConnect() MCCastingPlayer.stopConnecting() succeeded.")
58+
} else {
59+
self.connectionStatus = "Cancel connection failed due to: \(String(describing: err))."
60+
self.Log.error("MCConnectionExampleViewModel cancelConnect() MCCastingPlayer.stopConnecting() failed due to: \(err)")
61+
}
62+
}
63+
}
64+
}
65+
4566
func connect(selectedCastingPlayer: MCCastingPlayer?, useCommissionerGeneratedPasscode: Bool) {
4667
self.Log.info("MCConnectionExampleViewModel.connect() useCommissionerGeneratedPasscode: \(String(describing: useCommissionerGeneratedPasscode))")
4768

4869
let connectionCompleteCallback: (Swift.Error?) -> Void = { err in
4970
self.Log.error("MCConnectionExampleViewModel connect() completed with: \(err)")
5071
DispatchQueue.main.async {
5172
if err == nil {
73+
self.pendingPasscodeConfirmation = false;
5274
self.connectionSuccess = true
5375
if useCommissionerGeneratedPasscode {
5476
self.connectionStatus = "Successfully connected to Casting Player using the Casting Player/Commissioner-Generated passcode!"
@@ -125,6 +147,7 @@ class MCConnectionExampleViewModel: ObservableObject {
125147
self.Log.info("MCConnectionExampleViewModel connect() commissionerDeclarationCallback, calling MCCastingPlayer.continueConnecting()")
126148
let errContinue = selectedCastingPlayer?.continueConnecting()
127149
if errContinue == nil {
150+
self.pendingPasscodeConfirmation = false;
128151
self.connectionStatus = "Continuing to connect with user entered passcode: \(userEnteredPasscode)"
129152
} else {
130153
self.connectionStatus = "Continue Connecting to Casting Player failed with: \(String(describing: errContinue)) \n\nRoute back and try again."
@@ -142,6 +165,7 @@ class MCConnectionExampleViewModel: ObservableObject {
142165
self.Log.info("MCConnectionExampleViewModel connect() commissionerDeclarationCallback, Connection attempt cancelled by the user, calling MCCastingPlayer.stopConnecting()")
143166
let err = selectedCastingPlayer?.stopConnecting()
144167
self.connectionSuccess = false
168+
self.pendingPasscodeConfirmation = false;
145169
if err == nil {
146170
self.connectionStatus = "User cancelled the connection attempt with CastingPlayer. \n\nRoute back to exit."
147171
self.Log.info("MCConnectionExampleViewModel connect() commissionerDeclarationCallback, User cancelled the connection attempt with MCCastingPlayer, MCCastingPlayer.stopConnecting() succeeded.")
@@ -180,7 +204,10 @@ class MCConnectionExampleViewModel: ObservableObject {
180204

181205
self.Log.info("MCConnectionExampleViewModel.connect() calling MCCastingPlayer.verifyOrEstablishConnection()")
182206
let err = selectedCastingPlayer?.verifyOrEstablishConnection(with: connectionCallbacks, identificationDeclarationOptions: identificationDeclarationOptions)
183-
if err != nil {
207+
if err == nil {
208+
self.pendingPasscodeConfirmation = true;
209+
} else {
210+
self.pendingPasscodeConfirmation = false;
184211
self.Log.error("MCConnectionExampleViewModel connect(), MCCastingPlayer.verifyOrEstablishConnection() failed due to: \(err)")
185212
}
186213
}

examples/tv-casting-app/tv-casting-common/core/CastingPlayer.cpp

-5
Original file line numberDiff line numberDiff line change
@@ -228,11 +228,6 @@ CHIP_ERROR CastingPlayer::ContinueConnecting()
228228

229229
CHIP_ERROR CastingPlayer::StopConnecting()
230230
{
231-
VerifyOrReturnValue(
232-
mIdOptions.mCommissionerPasscode, CHIP_ERROR_INCORRECT_STATE,
233-
ChipLogError(AppServer,
234-
"CastingPlayer::StopConnecting() mIdOptions.mCommissionerPasscode == false, ContinueConnecting() should only "
235-
"be called when the CastingPlayer/Commissioner-Generated passcode commissioning flow is in progress."););
236231
// Calling the internal StopConnecting() API with the shouldSendIdentificationDeclarationMessage set to true to notify the
237232
// CastingPlayer/Commissioner that the commissioning session was cancelled by the Casting Client/Commissionee user. This will
238233
// result in the Casting Client/Commissionee sending a CancelPasscode IdentificationDeclaration message to the CastingPlayer.

0 commit comments

Comments
 (0)