This tech tip cover profiles and savepoints.
A profile allows a player to have different settings than other players.
A profile can be used to make the game harder for a skilled player, this way a novice player can enjoy a more balanced experience when playing together. A profile can also be used to adjust the settings according to each family member preference.
Only some settings can be customized per profile as determined by each application. For some settings, it does not make sense to have different values per player (like the number of balls per game or the number of credits per game), so these cannot be in the profile.
When there is no profile, all the settings are taken from the global settings in the service menu. This is what you get when you choose <None> for the profile.
When a profile is active for a player, the settings customizable per profile are taken from the profile, and the other settings are taken from the global settings.
The Default Profile is the profile assigned to players that are added with the Start button. The player can change his profile before playing his first ball. It is also possible to add players with a specific profile in the feature menu.
When Team Game is enabled, players with the same profile are considered to be in the same team and combine their scores. Team Games are not eligible for achievements like replays or entering high scores. It is possible to have a single player in a team (if none of the other players have the same profile).
A savepoint stores the progress of the player within the game up to that point. A savepoint is tied to a specific profile. A profile can have many savepoints except the <None> profile which does not support savepoints. The only time you can save a savepoint is when the ball is pending launch. When saving, you can create a new savepoint or overwrite an existing savepoint.
A savepoint can be restored when the ball is pending launch. This restores the progress within the game to the point when the savepoint was saved. The score is restored but the ball number is not affected. If you restore a savepoint on ball 1, you get to play the full 3-ball game. If you restore on ball 2, your progress and your score is replaced by the savepoint and you continue to play from ball 2.
The feature menu is documented here file:///C:/P3/P3_SDK_V0.8/P3SampleApp/Documentation/html/_additional_platform_features.html#FeatureMenu
To display the feature menu, hold one of the lower flipper buttons and press Start.
In the simulator, that would be: press a and while still holding a, press s. The feature menu is fully operational when running P3SampleApp in the simulator.
Be aware P3SampleApp has some bugs in button legends: the left and right buttons are swapped; and sometimes the buttons are mislabeled (even after considering the swap).
In Attract mode, the feature menu lets you:
On ball 1 pending launch, the feature menu lets you:
On ball 2 or more pending launch, the feature menu lets you:
Note: it is not possible to display the feature menu when the ball is in play.
The savepoint options are not available when the player has no profile (<None> profile).
You cannot remove a player if there is only one player left.
The operator can configure the contents of the feature menu by removing some options through some settings. See file:///C:/P3/P3_SDK_V0.8/P3SampleApp/Documentation/html/_persistent_data.html#FeatureMenuGameAttributes
A Stock Profile is a set of settings with factory chosen values. For example, a game can define Easy, Medium and Hard stock profiles. See file:///C:/P3/P3_SDK_V0.8/P3SampleApp/Documentation/html/_persistent_data.html#StockProfiles
When a regular (non-stock) profile is created, it copies all the profile customizable settings from the base profile:
If the game defines no stock profiles, the base profile consists of the global settings.
If the game defines a single stock profile, the base profile is that stock profile.
If the game defines multiple stock profiles, the player must choose which one serves as the base profile in the menu.
The default profile and the currently active profile are not involved in the creation of new profiles.
The application decides if an attribute copied from a stock profile is read-only or not.
If the game is upgraded and it defines a new profile customizable settings, that settings will be added to the profile when the game accesses it for the first time.
The CreateStockProfiles() method in <appcode>GameAttributeManagerMode is where the stock profiles are created. P3SampleApp defines no stock profiles, but the code needed is shown in comments.
WAMONH does not define Stock Profiles, so maybe this feature is obsolescent.
A settings is implemented by a GameAttribute. For more information, see the Tech Tip Declaring Game Attributes.
A GameAttribute is customizable per profile if it has the GameAttributeOptions.ProfileOption.
The PRW and PTV constants also include the ProfileOption.
This example taken from P3SASettingsMode shows how to create a profile settings:
InitAttr(37, "BallSaveTime", "Ball Save Time", "Ball Save Time", "Service Menu/Settings/Gameplay/General", PRW, 15, 0, 20, 1, 15);
The player’s profile is activated when the player becomes active (it is his turn to play).
The profile assigned to a player is stored in the Player’s Data:
string profileName = data.currentPlayer.GetData(ProfileManagerMode.DATAKEY_PROFILE, ProfileManagerMode.NONE_PROFILE);
To determine if the player has no profile, compare the name against the <None> profile:
if (profileName == ProfileManagerMode.NONE_PROFILE) { … }
Unless you are coding profile management, this is rarely needed. To get the value of a GameAttribute that can vary per profile, simply get the game attribute as usual:
int numAliens = data.GetGameAttributeValue("NumAliens").ToInt();
The attribute is looked up under the profile first, and if not found it is looked up in the global settings.
The player name is the profile name. This can be <None> if the player has no profile. The method returns "PlayerNotInGame" if the player index is >= the number of players in the game.
string playerName = data.GetPlayerName(x);
The following method variant will return "Player " + (x+1).ToString() instead of returning <None>. This is what the apron display does.
string playerName = data.GetPlayerName(x, true);
The current player number is data.currentPlayerIndex, the value ranges from 0 to data.Players.Count – 1
To access Event Profiles, open the service menu, select Statistics, select Create an event profile.
The name “Event Profile” is unfortunate because it has nothing to do with mode to mode events, nor player profiles discussed earlier. Event here means a happening that brings people together, like a pinball convention, a pinball tournament, etc… Profile here means data that describes the specific attributes, like a population profile.
An Event Profile gathers usage statistics for the duration of an event. You can have multiple Event Profiles gathering usage statistics at the same time. The difference with regular statistics is the operator decides when to start and stop collecting data for each Event Profile.
Unfortunately, this feature is broken in P3SampleApp because the EventNameEditor prefab is missing. It is also broken in WAMONH 1.0.2.1 probably for the same reason. These are the only two games I tested.
“For Amusement Only” wrote in their release notes they fixed this problem in their games in August 2023.
Profiles and savepoints are stored in the .multimorphic directory under the user’s home directory. This is also where the high score database, statistics and the module drivers are stored.
Path under ~/.multimorphic/P3/ | Description |
Data/<appcode>/EventProfiles/* | Statistics gathered during an event |
Data/<appcode>/HighScores.db | High Scores for this app |
Data/<appcode>/settings.db | Global settings for this app |
Data/<appcode>/Statistics.db | Statistics for this app |
Data/PlayfieldModules/LocalDataModule<ModuleId>LocalSettings.db | Simulator storage for settings normally stored on the module USB drive |
Data/PlayfieldModules/Module<ModuleId>Settings.db | Module specific settings stored on the machine |
Data/Settings.db | Global settings for the machine |
DefaultProfiles/<ProfileName>/<appcode>/settings.db | Stock profile for this app |
ModuleDrivers/<ModuleId>/<version>/<moduleid>-diags-assets | Diagnostics app for this module |
ModuleDrivers/<ModuleId>/<version>/<ModuleId>.dll | Module driver |
ModuleDrivers/<ModuleId>/<version>/<ModuleId>.json | Module definition file |
ModuleDrivers/<ModuleId>/<version>/* | Module documentation for developers |
PlayerProfiles/<ProfileName>/<appcode>/Achievements.db | Achievements for this profile and app** |
PlayerProfiles/<ProfileName>/<appcode>/SavedGames/<savepoint>.gamestate | Savepoint state storage |
PlayerProfiles/<ProfileName>/<appcode>/settings.db | Profile specific settings for this app |
** The only profile specific achievement is: “100 Games Played”.