@@ -116,22 +116,13 @@ class _ProductsScreenState extends State<ProductsScreen> {
116116 debugPrint ('🔄 [Qonversion] Purchasing product: ${product .qonversionId }...' );
117117 final result = await Qonversion .getSharedInstance ().purchaseWithResult (product);
118118
119+ // Show full PurchaseResult details
120+ _showPurchaseResultDialog (result);
121+
119122 if (result.isSuccess) {
120123 debugPrint ('✅ [Qonversion] Purchase successful!' );
121- debugPrint (' Transaction ID: ${result .storeTransaction ?.transactionId }' );
122- _showSuccess ('Purchase successful!' );
123-
124124 // Update entitlements
125125 appState.setEntitlements (result.entitlements);
126- } else if (result.isCanceled) {
127- debugPrint ('ℹ️ [Qonversion] Purchase canceled by user' );
128- _showInfo ('Purchase canceled' );
129- } else if (result.isPending) {
130- debugPrint ('ℹ️ [Qonversion] Purchase pending' );
131- _showInfo ('Purchase is pending' );
132- } else if (result.isError) {
133- debugPrint ('❌ [Qonversion] Purchase failed: ${result .error ?.message }' );
134- _showError ('Purchase failed: ${result .error ?.message }' );
135126 }
136127 } catch (e) {
137128 debugPrint ('❌ [Qonversion] Purchase error: $e ' );
@@ -141,6 +132,92 @@ class _ProductsScreenState extends State<ProductsScreen> {
141132 }
142133 }
143134
135+ void _showPurchaseResultDialog (QPurchaseResult result) {
136+ final tx = result.storeTransaction;
137+
138+ showDialog (
139+ context: context,
140+ builder: (context) => AlertDialog (
141+ title: Row (
142+ children: [
143+ Icon (
144+ result.isSuccess ? Icons .check_circle :
145+ result.isCanceled ? Icons .cancel :
146+ result.isPending ? Icons .pending : Icons .error,
147+ color: result.isSuccess ? Colors .green :
148+ result.isCanceled ? Colors .orange :
149+ result.isPending ? Colors .blue : Colors .red,
150+ ),
151+ const SizedBox (width: 8 ),
152+ Text ('Purchase Result' ),
153+ ],
154+ ),
155+ content: SingleChildScrollView (
156+ child: Column (
157+ crossAxisAlignment: CrossAxisAlignment .start,
158+ mainAxisSize: MainAxisSize .min,
159+ children: [
160+ _buildResultRow ('Status' , result.status.name),
161+ _buildResultRow ('Source' , result.source.name),
162+ _buildResultRow ('Is Fallback' , result.isFallbackGenerated.toString ()),
163+ if (result.error != null ) ...[
164+ const Divider (),
165+ _buildResultRow ('Error Code' , result.error! .code.toString ()),
166+ _buildResultRow ('Error Message' , result.error! .message ?? 'N/A' ),
167+ ],
168+ if (tx != null ) ...[
169+ const Divider (),
170+ const Text ('Store Transaction:' , style: TextStyle (fontWeight: FontWeight .bold)),
171+ const SizedBox (height: 8 ),
172+ _buildResultRow ('Transaction ID' , tx.transactionId ?? 'N/A' ),
173+ _buildResultRow ('Original TX ID' , tx.originalTransactionId ?? 'N/A' ),
174+ _buildResultRow ('Product ID' , tx.productId ?? 'N/A' ),
175+ _buildResultRow ('Quantity' , tx.quantity? .toString () ?? 'N/A' ),
176+ _buildResultRow ('TX Date' , tx.transactionDate? .toIso8601String () ?? 'N/A' ),
177+ _buildResultRow ('Promo Offer ID' , tx.promoOfferId ?? 'N/A' ),
178+ _buildResultRow ('Purchase Token' , tx.purchaseToken != null
179+ ? '${tx .purchaseToken !.substring (0 , 20 )}...'
180+ : 'N/A' ),
181+ ],
182+ if (result.entitlements != null && result.entitlements! .isNotEmpty) ...[
183+ const Divider (),
184+ Text ('Entitlements (${result .entitlements !.length }):' ,
185+ style: const TextStyle (fontWeight: FontWeight .bold)),
186+ const SizedBox (height: 8 ),
187+ ...result.entitlements! .values.map ((e) => Padding (
188+ padding: const EdgeInsets .only (bottom: 4 ),
189+ child: Text ('• ${e .id } (active: ${e .isActive })' ),
190+ )),
191+ ],
192+ ],
193+ ),
194+ ),
195+ actions: [
196+ TextButton (
197+ onPressed: () => Navigator .of (context).pop (),
198+ child: const Text ('OK' ),
199+ ),
200+ ],
201+ ),
202+ );
203+ }
204+
205+ Widget _buildResultRow (String label, String value) {
206+ return Padding (
207+ padding: const EdgeInsets .symmetric (vertical: 2 ),
208+ child: Row (
209+ crossAxisAlignment: CrossAxisAlignment .start,
210+ children: [
211+ SizedBox (
212+ width: 110 ,
213+ child: Text ('$label :' , style: const TextStyle (fontWeight: FontWeight .w500)),
214+ ),
215+ Expanded (child: Text (value, style: const TextStyle (fontFamily: 'monospace' ))),
216+ ],
217+ ),
218+ );
219+ }
220+
144221 void _showSuccess (String message) {
145222 ScaffoldMessenger .of (context).showSnackBar (
146223 SnackBar (
0 commit comments