XaiJu
__ess__
__ess__

patreon


Ren'Py Gardening/Planting Mini-game Script Now Available!

The gardening/planting mini-game is now finished and available for download at be bottom of this post for anyone in the Supporter tier or higher! ๐Ÿ˜

Watch the preview video above and read the post below to learn how it works. I'll only go through some of the more important aspects of the script in this post, as there's also a lot of comments in the script to guide you.

As usual, using my scripts requires you to have at least a basic understanding of how to use Ren'Py like: how to use screens and labels, how to show images, how to use actions and be familiar with different types and what variables are. Otherwise my mini-games can be too challenging to use and customize to your needs. Preferably, you'd also know a little Python too.

How does it work?

The script adds a separate mini-game screen that acts as the player's garden where they can, in this example, plant up to 8 plants in 8 different slots. Each plant will take different amount of time to grow depending on how you set it up.

The images

Each stage of the plant's growth have 4 different images, where 2 of them are unique to the specific plant that's growing.

The first two images are generic ones that are shared between all plants (planted-seed.png, flower-sprout.png) and represents the first two stages of the plant. The next two images are numbered 1 and 2 where 2 is the final stage.

So take the pink flower as an example, as it grows, it will first show "planted-seed.png" and then the "flower-sprout.png" image. Then the next stage will be "pink-flower-1.png" and then "pink-flower-2". It will make more sense when you test the game and also look into the code a bit. ๐Ÿ˜‰

The plants will need to be watered regularly according to how you choose to set it up. In the example script, I set it so every 5 second that passes of each plant's progression timer, the plant will loose 1 unit of water out of a total of 100. This is set in the "change_plant_time" function. Clicking on the hose allows you to then water a plant which will top it to 100%.

If the plant completely runs out of water, the plant will stop growing rather than die off.

Important notes about adding your own images

When you change to using your own images, please make sure that each plant image (seed planted, sprout etc.) are the same size. This is so they'll align nicely in the mini-game screen. Then make sure in the mini-game screen that you change the size of the container frame for the plants (on line 206) so it will fit both a dirt patch and any of your plant images.

Saving/loading

Saving and loading should work while showing the mini-game screen. This is due to the use of "renpy.retain_after_load()" at the end of some of the mini-game functions, and the use of the label "after_load" to make sure the plant timers start back up after loading a save.

In short basic terms: changes that happens to variables in functions won't save automatically until the next "interaction" occurs. In screens, these types of interactions doesn't occur, and as such the changes to variables in functions won't automatically save when the player saves the game. That's where the retain_after_load() function comes in handy, as it will force Ren'Py to save the variable changes when the game saves.

Please read up about these things to learn how they work and when to use them before using them in your own code:

The gardening inventory

The player gets a gardening inventory where all the seeds they can plant will be located. This you can setup before the game starts and/or add as the game progresses, such as if the player buys more seeds for example.

This information is stored in the dictionary variable called "gardening_inventory" where each entry stores how many of a certain seed the player has, how long it takes for a seed to fully mature etc.

The key of each entry should be the same as the inventory slot image of that particular seed, minus the word "slot". So in this example, we have a "pink flower seed" which has an inventory image called "pink-flower-seed-slot", and as such the key for it in the dictionary is "pink-flower-seed".

I've included a function "pickup_seed" to add a new item to the dictionary that you can call at anytime in your visual novel when the player is supposed to gain a new seed, or to top up seeds they already have. An example of how to use it is in the main script.rpy file in the label "test_label".

Keeping track of plants

To keep track of the planted seeds, and to be able to update their info over time, I've created another dictionary called "planted". You can see how it's used in the function "item_select".

This dictionary simply keeps track of which dirt patch a plant belongs to, how far along its progression timer is currently, what "growth stage" it's currently in and so on. Every time the player clicks on a seed in the inventory to plant it, the function called "item_select" runs and adds a new entry to this dictionary.

First the player needs to click on a dirt patch, which sets the variable "selected_dirt_patch" to a number between 0-7 which represents the dirt patch selected. So the first patch is 0, second is 1 etc. Let's say they click on the third one, which makes the variable equal to 2.

Then the player picks a seed in the inventory, and after clicking it, the planted dictionary gets a new entry with the key "2" together with the information about the plant in this spot.

The screens

Mini-game screen

There's a few screens in this mini-game script. The first one is the actual mini-game screen called "growing_plants". This screen is pretty long, as it has a lot of displayables in it. We have a few buttons like the hose, and the "exit" button that lets you leave the mini-game.

Then we have the actual dirt patches which are inside a grid inside a frame. In the grid is a loop that loops 8 times to add empty dirt patches, or dirt + plants if there are any planted.

The plants images are added by checking which stage it is currently in.

We only have 4 stages for each plant, so when you design images for your game, you'll want to add the same. This script assumes the first two images are generic, as I described at the beginning of this post (seed planted and sprout stage). Then stage 3 and 4 are the actual unique plant images, hence why we use string interpolation to pick the correct filename.

The 4th one is an imagebutton so you can click it to harvest the plant. It runs the function "harvest_plant" which removes the plant from the dirt. In this function you can add your own logic to add the plant to your game's inventory system or do something different with the plant that was just picked. The example code in it calls a screen (picked_plant) to show up with the image of the plant that was just picked, and the name of it.

We also have the progress bars in the mini-game screen for the growth status and the water status. The time progression bar is formatted to show in minutes:seconds using a Python module called "time". You can look it up in the Python documentation if you're curious about it.

Inventory screen

We also have the gardening inventory screen I've called "planting_inventory". It will only show its contents if Ren'Py has captured focus of a dirt patch. To capture focus, we use the CaptureFocus() action which runs when the player clicks on an empty dirt patch in the mini-game screen (see line 278 in the mini-game script file).

In the inventory screen we then do an if statement to check if there's focus on a dirt patch or not, and if there is, we add the displayables that shows the inventory.

There's a tooltip functionality at the bottom of the screen that shows the name of the currently hovered inventory item. This one also requires focus to be captured by one of the items. You can see this happening on line 326. You can also read more about tooltips on Ren'Py's documentation page: https://www.renpy.org/doc/html/screen_actions.html#tooltips

Plant progress timer screen

Another screen I'll mention here as well is the "plant_timers" screen. This screen is called when the first seed has been planted and is kept active throughout the game (it's shown in the item_selected function). It doesn't actually show anything visually as it just contains a timer displayable that calls a function (change_plant_time) to decrease each plant's growing time every second, as well as decrease the water availability in the soil.

How to use the script

To use the script, you can copy the planting_minigame.rpy script into your own project and make sure you have images to use for it as well. You can adjust any positioning and sizes to fit your own game.

I don't think I've forgotten anything important, but if you still have questions you can leave them in the comments below. I'll make sure to update the post if I feel like I need to add some more information to it.

If you encounter something that's not working correctly that you think might be a bug, feel free to let me know as I regularly go through bug reports to fix code that's either outdated or not functioning properly otherwise.

Enjoy! ๐Ÿ˜Š๐ŸŒผ๐ŸŒฟ

Comments

Hi! Thanks for reporting the issue! ๐Ÿ‘ It has now been fixed. It was an error with the tooltip in the inventory screen due to that the code was trying to access the hovered item to show its name after the item got depleted/removed. I have added another condition to the if statement for the tooltip which has fixed the error. You can download the new version and it should work now. Glad to hear you like my scripts, appreciate you letting me know! ๐Ÿ˜

Sara

Hi! I absolutely love all of your mini games! But, I am getting an error on your sample game if I try to plant the last seed of each stack. It says error pink_flower_seed or error yellow_flower_seed if I plant the last seed of a stack. Otherwise, the plants grow as expected. Thank you so much! You do incredible work!

John Sweeting

Glad to hear it Pytem! Thanks for the feedback, appreciate it as always. ๐Ÿ‘

Sara

Damn, this is even better than I expected! You really made an awesome job!

Pytem


More Creators