Ultra complexe Save Error which is completely beyond me

Discuss how to use the Ren'Py engine to create visual novels and story-based games. New releases are announced in this section.
Forum rules
This is the right place for Ren'Py help. Please ask one question per thread, use a descriptive subject like 'NotFound error in option.rpy' , and include all the relevant information - especially any relevant code and traceback messages. Use the code tag to format scripts.
Post Reply
Message
Author
User avatar
sculpteur
Veteran
Posts: 221
Joined: Fri Nov 17, 2017 6:40 pm
Completed: Apocalypse Lovers
Projects: Apocalypse Lovers
Organization: Awake_Production
Location: France
Discord: https://discord.gg/apocalypse-lovers
Contact:

Ultra complexe Save Error which is completely beyond me

#1 Post by sculpteur » Sat Jul 30, 2022 1:28 pm

Hello I've got this error which occure in some situation and I'm unable to solve it with my corrent knowledge.
Please, a litlle help will be really appreciated :)

The error happens when :

> left click the square in menu to make a regular save.
> click the quick save
> press the quick save shortcut
> Also sometime when the player stay afk but the game is still running

More over, I've notice those kind of line don't work anymore in my game (it was working before):
Now it's now working but this is not triggering the error.

Code: Select all

    python:
        if not renpy.game.after_rollback:
            renpy.loadsave.force_autosave(True)

Code: Select all

$ renpy.loadsave.force_autosave(True)

This is the error :

Code: Select all

I'm sorry, but an uncaught exception occurred.

While running game code:
  File "renpy/common/00action_file.rpy", line 382, in __call__
    renpy.save(fn, extra_info=save_name)
Exception: Could not pickle <module 'time' (built-in)>. (perhaps renpy.game.log.log[66].stores[u'store']['time'] = <module 'time' (built-in)>)

-- Full Traceback ------------------------------------------------------------

Full traceback:
  File "renpy/common/_layout/screen_load_save.rpym", line 35, in script
    $ ui.interact()
  File "renpy/ast.py", line 928, in execute
    renpy.python.py_exec_bytecode(self.code.bytecode, self.hide, store=self.store)
  File "renpy/python.py", line 2245, in py_exec_bytecode
    exec(bytecode, globals, locals)
  File "renpy/common/_layout/screen_load_save.rpym", line 35, in <module>
    $ ui.interact()
  File "renpy/ui.py", line 298, in interact
    rv = renpy.game.interface.interact(roll_forward=roll_forward, **kwargs)
  File "renpy/display/core.py", line 3325, in interact
    repeat, rv = self.interact_core(preloads=preloads, trans_pause=trans_pause, pause=pause, pause_start=pause_start, **kwargs)
  File "renpy/display/core.py", line 4160, in interact_core
    rv = root_widget.event(ev, x, y, 0)
  File "renpy/display/layout.py", line 1102, in event
    rv = i.event(ev, x - xo, y - yo, cst)
  File "renpy/display/layout.py", line 1102, in event
    rv = i.event(ev, x - xo, y - yo, cst)
  File "renpy/display/layout.py", line 1102, in event
    rv = i.event(ev, x - xo, y - yo, cst)
  File "renpy/display/screen.py", line 727, in event
    rv = self.child.event(ev, x, y, st)
  File "renpy/display/layout.py", line 1102, in event
    rv = i.event(ev, x - xo, y - yo, cst)
  File "renpy/display/layout.py", line 1323, in event
    rv = super(Window, self).event(ev, x, y, st)
  File "renpy/display/layout.py", line 273, in event
    rv = d.event(ev, x - xo, y - yo, st)
  File "renpy/display/layout.py", line 1102, in event
    rv = i.event(ev, x - xo, y - yo, cst)
  File "renpy/display/layout.py", line 1323, in event
    rv = super(Window, self).event(ev, x, y, st)
  File "renpy/display/layout.py", line 273, in event
    rv = d.event(ev, x - xo, y - yo, st)
  File "renpy/display/layout.py", line 1102, in event
    rv = i.event(ev, x - xo, y - yo, cst)
  File "renpy/display/layout.py", line 273, in event
    rv = d.event(ev, x - xo, y - yo, st)
  File "renpy/display/behavior.py", line 983, in event
    return handle_click(self.clicked)
  File "renpy/display/behavior.py", line 918, in handle_click
    rv = run(action)
  File "renpy/display/behavior.py", line 330, in run
    return action(*args, **kwargs)
  File "renpy/common/00action_file.rpy", line 382, in __call__
    renpy.save(fn, extra_info=save_name)
  File "renpy/loadsave.py", line 420, in save
    reraise(t, e, tb)
  File "renpy/loadsave.py", line 401, in save
    dump((roots, renpy.game.log), logf)
  File "renpy/loadsave.py", line 49, in dump
    cPickle.dump(o, f, cPickle.HIGHEST_PROTOCOL)
  File "renpy/python.py", line 2342, in module_pickle
    raise Exception("Could not pickle {!r}.".format(module))
Exception: Could not pickle <module 'time' (built-in)>. (perhaps renpy.game.log.log[66].stores[u'store']['time'] = <module 'time' (built-in)>)

Windows-8.1-6.3.9600
Ren'Py 7.4.11.2266
Apocalypse Lovers 1.16
Sat Jul 30 19:21:03 2022
Image

“He asked me to calm down, close my eyes and be quiet. He explained to me that if I was afraid, the shadow that ran barefoot in the street would feel it. I got scared seeing Jumanji on TV, so let me tell you, we didn't stay hidden for long and had to start running again.”
Jessica's Diary.

User avatar
Alex
Lemma-Class Veteran
Posts: 2981
Joined: Fri Dec 11, 2009 5:25 pm
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#2 Post by Alex » Sat Jul 30, 2022 3:14 pm

Do you have any variable/function/etc. named 'time' in your script?
Or how do you use time module in your functions?

User avatar
sculpteur
Veteran
Posts: 221
Joined: Fri Nov 17, 2017 6:40 pm
Completed: Apocalypse Lovers
Projects: Apocalypse Lovers
Organization: Awake_Production
Location: France
Discord: https://discord.gg/apocalypse-lovers
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#3 Post by sculpteur » Sun Jul 31, 2022 3:40 am

Hello, yes there is two system I used with time but I didn't done it from scratch and for one of them it's zmook (on this forum) who help me done it. So I don't handle all their aspect very well.
Take a look :

Code: Select all

################################################################################
## DELIRIUM WORDS SCREEN
################################################################################

## total duration of animation
define announcer_rise_time = 6  # in seconds
define announcer_yalign_end = 0.05
define announcer_zoom_end = 4
define delirium_words = ["Traitor", "Liar", "Fucking Liar", "Cheater", "Killer", "Burn", "Stupid", "Bastard", "Psycho", "Fucking", "Pervert", "Die", "Horror", "You", "Butcher", "Fucking Pervert", "Moron", "Guilty", "Creepy", "Cheater", "Murderer", "Crazy", "Sick", "Sicko", "Punishment", "Horrible", "Demon", "Guilt" ]
#define delirium_words = "Traitor Liar Cheater Killer Burn Stupid Bastard Psycho Fucking Pervert Die Kill Horror You Butcher Pervert Guilty Moron Creepy Bastard Liar Bastard Cheater Murderer Die Crazy Sick Die Punishment Horrible Demon Guilt".split()
define delirium_words_percentage = 50

transform announcer_float(startpos=(0.5, 0.5), endpos=(1.0,1.0), delay=0):
    # animation for the announced text.
    # floats the text to the top of the screen while it fades out.
    # x,y must be floats because the linear compares them to floats and it doesn't
    # work if they don't match.

    # starting position for the displayable
    pos startpos
    anchor (0.5, 0.5)
    zoom 0.01 alpha 0

    pause delay
    # make the displayable appear
    easein 0.15 zoom 1 alpha 1

    # drift, zoom and fade
    linear announcer_rise_time pos endpos zoom announcer_zoom_end alpha 0.


init python:
    import time, math

    # random number between (-0.5,0.5), for jitter
    def rr2():
        return renpy.random.random() - 0.5


    # calculates the x end position for the animation, radially away from the center
    # point with a little random jitter
    # you can mess around with this, it doesn't have to be perfect
    def announcer_pos_end(x_start, y_start):
        cp = (0.5 + 0.05*rr2(), 0.5 + 0.05*rr2())   # center point

        dx, dy = x_start-cp[0], y_start-cp[1]
        angle = math.atan2(dy, dx) + 0.05 * rr2()

        r_end = 0.5 + 0.3 * rr2()           # new radius to move to

        x_end = r_end * math.cos(angle) + cp[0]
        y_end = r_end * math.sin(angle) + cp[1]

        return (x_end, y_end)


    def announce(txt):
        display_id = "ann_%d" % hash(txt)
        delay = 0
        zorder = 8
        layer = 'screens'
        # randomize the position where the words appear
        start_x = 0.1 + 0.8*renpy.random.random()
        start_y = 0.1 + 0.8*renpy.random.random()
        endpos = announcer_pos_end(start_x, start_y)

        renpy.show(display_id, what=renpy.text.text.Text(txt, style="announce_text"), \
            layer=layer, \
            zorder=zorder, \
            at_list=[announcer_float((start_x, start_y), endpos, delay),])

        def hide_announce():
            time.sleep(announcer_rise_time)
            renpy.hide(display_id)

        renpy.invoke_in_thread(hide_announce)

        return


    def delirium_show_word(words):
        # we're checking frequently but only displaying a new word sometimes,
        # so that we get a randomized interval
        if renpy.random.randint(1,100) < delirium_words_percentage:
            word = renpy.random.choice(words)
            announce(word)

style announce_text is say_label:
    size 75
    outlines [ (absolute(1), "#000000", 2, 2) ]


screen delirium_words_screen():
    # how often do we *check* to maybe display a new word?
    default check_time = 0.1
    timer check_time repeat True action Function(delirium_show_word, delirium_words)
And the other one is this :

Code: Select all

################################################################################
## COOLDOWN SCREEN
################################################################################

#_______________________________________________________________________________
init -1 python:
    def countdown(st, at, length=0.0):# Countdown of the given length. White until 5 seconds are left, red until 0 seconds are left, and blink 0.0 when time is up.
        remaining = length - st
        if remaining > 3.0:
            return Text("{font=fonts/GoodDog.otf}%.1f{/font}" % remaining, color="#66cc00", size=82), .1
        elif remaining > 0.0:
            return Text("{font=fonts/GoodDog.otf}%.1f{/font}" % remaining, color="#f00", size=88), .1
        else:
            return anim.Blink(Text("{font=fonts/GoodDog.otf}0.0{/font}", color="#f00", size=90)), None
# Show a countdown for 12 seconds.
image countdown = DynamicDisplayable(countdown, length=9.0)
# Show a countdown for 6 seconds.
image countdown_fast = DynamicDisplayable(countdown, length=6.0)
#_______________________________________________________________________________
# POUR CHANGER LE TIMER : LIGNE A METTRE DANS LE CORPS DU CODE AVANT DISPLAY
    # $ ui.timer(12.0, ui.jumps("label"))
#_______________________________________________________________________________
transform alpha_dissolve:
    alpha 0.0
    linear 0.7 alpha 0.7
    on hide:
       linear 0.25 alpha 0
# This is to fade the bar in and out, and is only required once in your script
#_______________________________________________________________________________
# Countdown screen 2
init:
    # variable pour les menus à choix limité
    # time = the time the timer takes to count down to 0.
    # timer_range = a number matching time (bar only)
    # timer_jump = the label to jump to when time runs out
    $ timer_range = 0
    $ timer_jump = 0

screen countdown:
    modal True
    text _("Make a choice") xalign 0.5 yalign 0.05 size 20 color "#66cc00" bold 1 outlines [ (absolute(2), "#000", absolute(1), absolute(1)) ]
    timer 0.025 repeat True action If(time > 0, true=SetVariable('time', time - 0.025), false=[Hide('countdown'), Jump(timer_jump)])
    bar value time range timer_range xalign 0.5 yalign 0.87 ysize 18 xmaximum 1100 left_bar "#66cc00" right_bar "#000000" at alpha_dissolve # This is the timer bar.
#_______________________________________________________________________________
Image

“He asked me to calm down, close my eyes and be quiet. He explained to me that if I was afraid, the shadow that ran barefoot in the street would feel it. I got scared seeing Jumanji on TV, so let me tell you, we didn't stay hidden for long and had to start running again.”
Jessica's Diary.

User avatar
sculpteur
Veteran
Posts: 221
Joined: Fri Nov 17, 2017 6:40 pm
Completed: Apocalypse Lovers
Projects: Apocalypse Lovers
Organization: Awake_Production
Location: France
Discord: https://discord.gg/apocalypse-lovers
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#4 Post by sculpteur » Sun Jul 31, 2022 3:43 am

But if you want my amateur opinion, I found those two part suspicious :

Code: Select all

init python:
    import time, math

Code: Select all

    timer 0.025 repeat True action If(time > 0, true=SetVariable('time', time - 0.025), false=[Hide('countdown'), Jump(timer_jump)])
    bar value time range timer_range xalign 0.5 yalign 0.87 ysize 18 xmaximum 1100 left_bar "#66cc00" right_bar "#000000" at alpha_dissolve # This is the timer bar.
It's the only time I think "time" is mentionned more or less directly.
Image

“He asked me to calm down, close my eyes and be quiet. He explained to me that if I was afraid, the shadow that ran barefoot in the street would feel it. I got scared seeing Jumanji on TV, so let me tell you, we didn't stay hidden for long and had to start running again.”
Jessica's Diary.

User avatar
Ocelot
Eileen-Class Veteran
Posts: 1882
Joined: Tue Aug 23, 2016 10:35 am
Github: MiiNiPaa
Discord: MiiNiPaa#4384
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#5 Post by Ocelot » Sun Jul 31, 2022 4:19 am

Yes, the second screen conflict with first. What happens: seconds screens sets "time" store variable. THis action adds that varable name to a list of things you need to save. Then first screen imports time, overwriting "time": it is now a module. This does not add "time" to a list of variables to save, but that does not matter, since it is already here. The game saves, tries to save "time" (a module) and crashes, because it can't save module.

The solution is to not use name "time" in second screen.
< < insert Rick Cook quote here > >

User avatar
sculpteur
Veteran
Posts: 221
Joined: Fri Nov 17, 2017 6:40 pm
Completed: Apocalypse Lovers
Projects: Apocalypse Lovers
Organization: Awake_Production
Location: France
Discord: https://discord.gg/apocalypse-lovers
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#6 Post by sculpteur » Mon Aug 01, 2022 2:59 am

Hey !

Yes I was suspecting something like this. So what would you recommand to change exactly ?
I suppose I should change the name on one of the 'time' variable, like 'time_2' or something.
But I'm not sure which one should I choose to stay as much simpliest as possible because I'm afraid to mess up with the code by doing this :lol:
Image

“He asked me to calm down, close my eyes and be quiet. He explained to me that if I was afraid, the shadow that ran barefoot in the street would feel it. I got scared seeing Jumanji on TV, so let me tell you, we didn't stay hidden for long and had to start running again.”
Jessica's Diary.

User avatar
Ocelot
Eileen-Class Veteran
Posts: 1882
Joined: Tue Aug 23, 2016 10:35 am
Github: MiiNiPaa
Discord: MiiNiPaa#4384
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#7 Post by Ocelot » Mon Aug 01, 2022 3:29 am

Change the second screen variable name. I would choose timer_time to be in line with other varables in that screen. And change all mentions of "time" there to new name.

While you can rename imported module, I would advise against it in this case.
< < insert Rick Cook quote here > >

User avatar
sculpteur
Veteran
Posts: 221
Joined: Fri Nov 17, 2017 6:40 pm
Completed: Apocalypse Lovers
Projects: Apocalypse Lovers
Organization: Awake_Production
Location: France
Discord: https://discord.gg/apocalypse-lovers
Contact:

Re: Ultra complexe Save Error which is completely beyond me

#8 Post by sculpteur » Thu Aug 04, 2022 4:10 pm

Hey !

Yeah thanks, good call, this is perfectly fixing the issue !
Image

“He asked me to calm down, close my eyes and be quiet. He explained to me that if I was afraid, the shadow that ran barefoot in the street would feel it. I got scared seeing Jumanji on TV, so let me tell you, we didn't stay hidden for long and had to start running again.”
Jessica's Diary.

Post Reply

Who is online

Users browsing this forum: Google [Bot]