Visually Located

XAML and GIS

Increasing in app purchases in your Windows Phone apps

There are a few ways to increase the rate of in app purchases. One of these ways is to show a message prompt to the user explaining that an in app purchase is available and what the user can get from it. In a previous post I explained how to use Telerik’s RateApplicationReminder to increase reviews of your app. The RateApplicationReminder is great because it just works. No, really. No need for you to determine if you should show a reminder to rate the app. It handles all of the logic and it navigates the user to rate your app. Another benefit of the RateApplicationReminder is that it is built on a framework for showing reminders. This framework can be extended to create your own reminders.

The is a decent framework to build reminders on. It has one abstract method, GetDataFilePath. This is just a file name for the data that will be saved. It has two virtual methods that can be overridden, but the power is in the properties that it has

// Summary:
// Setting this property to True will display a checkbox in the reminder that
// will allow users to skip further notifications.
public bool AllowUsersToSkipFurtherReminders { get; set; }
//
// Summary:
// Gets or sets a value indicating whether further reminders will be skipped.
public bool AreFurtherRemindersSkipped { get; set; }
//
// Summary:
// Gets the last date when reminder was displayed.
public ReminderBase DateTime? LastReminderDisplayDate { get; }
//
// Summary:
// Gets the number of app runs after the last reminder was displayed.
public int NumberOfUsagesAfterLastReminder { get; internal set; }
//
// Summary:
// Gets the persisted data.
protected T PersistedData { get; }

These properties a big part of when and if you should show a reminder. The RateApplicationReminder has some additional properties that dictate how many times (or the time frame) the app should open before showing a reminder. These properties are great for an in app purchase reminder as well. We’ll start there for our reminder

/// <summary>
/// Gets or sets the number of application runs on which the reminders will be displayed.
/// </summary>
public int? RecurrencePerUsageCount { get; set; }
 
/// <summary>
/// Gets or sets the time period on which the reminders will be displayed.
/// </summary>
public TimeSpan? RecurrencePerTimePeriod { get; set; }
 
/// <summary>
/// Gets or sets the information that will be displayed in the message box.
/// </summary>
public MessageBoxInfoModel MessageBoxInfo { get; set; }

The MessageBoxInfo determines what text should be shown to the user when the reminder is shown.You’ll want to have some default values for this.

public InAppPurchaseReminder()
{
    MessageBoxInfo = new MessageBoxInfoModel
        {
            Buttons = MessageBoxButtons.YesNo,
            SkipFurtherRemindersMessage = "Do not show this reminder again",
            Title = "In App Purchase"
        };
}

The ReminderBase class has the method, ShowReminderMessage, to show the reminder. When this is called the reminder will be shown even if it should not be. To ensure that the reminder is only shown when it is suppose to, the RateApplicationReminder has a Notify method that you call instead. The Notify method is where it is determined if it should be shown or not.

/// <summary>
/// Notifies the user of the in app purchase.
/// </summary>
public void Notify()
{
    IncreaseUsageCount();
    if (ShouldShowReminder() == false) return;
 
    var args = new CancelEventArgs();
    OnShowing(args);
    if (args.Cancel) return;
 
    ShowReminderMessage(MessageBoxInfo);
}
 
private void IncreaseUsageCount()
{
    // If the reminder has been shown at least once, and we're tracking usage count
    if (LastReminderDisplayDate.HasValue && RecurrencePerUsageCount.HasValue &&
        RecurrencePerUsageCount.Value > 0)
    {
        PersistedData.NumberOfAppRunsAfterLastReminder++;
        SavePersistedData();
    }
}
 
private bool ShouldShowReminder()
{
    if (LastReminderDisplayDate.HasValue && AreFurtherRemindersSkipped) return false;
 
    // priorty on usage count, calculate first
    if (RecurrencePerUsageCount.HasValue)
    {
        var numUsage = LastReminderDisplayDate.HasValue
                           ? NumberOfUsagesAfterLastReminder
                           : ApplicationUsageHelper.ApplicationRunsCountTotal;
 
        if (numUsage >= RecurrencePerUsageCount) return true;
    }
    // if no usage count, or the value has not been met, try time period
    if (RecurrencePerTimePeriod.HasValue)
    {
        var timeSpan = DateTime.Now - (LastReminderDisplayDate.HasValue
                                           ? LastReminderDisplayDate.Value
                                           : ApplicationUsageHelper.InitialInstallationDate);
        if (timeSpan >= RecurrencePerTimePeriod.Value) return true;
    }
 
    return false;
}

The Notify method calls the OnShowing method to notify you code that the dialog is going to be shown. It also gives event listeners a chance to stop the reminder from showing. If everything works out well, it shows the dialog. Inside IncreaseUsageCount, we call the SavePersistedData method. This will save any information that is in the ReminderBaseDataModel that is part of the class. For this reminder, we incremented the NumberOfAppRunsAfterLastReminder property. When the SavePersistedData method is called, it calls into the GetDataFilePath so it knows where to write the file of information.

/// <summary>
/// Gets or sets the product ID for the reminder .
/// </summary>
public string ProductID { get; set; }
 
protected override string GetDataFilePath()
{
    if (ProductID == null)
        throw new InvalidOperationException("ProductID property not specified.");
 
    return string.Format("PurchaseReminder_{0}.xml", ProductID);
}

To save the file, we’ll use the product id of the in app purchase. This guarantees us a unique file name for the application. The last thing to do is to show the in app purchase to the user if they decide to hit the yes button. To do this we need to override the OnReminderMessageClosed method.

protected override async void OnReminderMessageClosed(ReminderClosedEventArgs args)
{
    base.OnReminderMessageClosed(args);
 
    if (args.MessageBoxEventArgs.Result != DialogResult.OK) return;
 
    // Show the in ap purchase to the user if they tapped the yes button
    try
    {
        await CurrentApp.RequestProductPurchaseAsync(ProductID, false);
 
        if (CurrentApp.LicenseInformation.ProductLicenses[ProductID].IsActive)
        {
            AreFurtherRemindersSkipped = true;
 
            // If the IAP is a durable do the following
            // CurrentApp.ReportProductFulfillment(ProductID);
 
           // TODO: Fire an event thgat states that the purchase was made.
        }
    }
    catch (Exception)
    {
    }
}

Using the reminder is pretty simple. Here is an example to remove ads.

var reminder = new InAppPurchaseReminder()
{
    AllowUsersToSkipFurtherReminders = true,
    ProductID = "RemoveAdProductID",
};
 
reminder.MessageBoxInfo.Content =
    "Did you know that you can remove the ads and help support this app? Would you like to remove the ads now?";
reminder.MessageBoxInfo.Title = "Remove ads?";
// show on every tenth open of the app
reminder.RecurrencePerUsageCount = 10;
reminder.Notify();

You can download the complete file here. Good luck!

blog comments powered by Disqus