Open FastusNumen opened 11 months ago
Thanks for the Link to this awesome tool, but I think, this is a copy of my Issue #155!
Regards
No, I knew that issue, you already linked to that in this one #1221. If I got it right, you meant to have the time and date on each scene.
This is different. I meant to have an actual calendar in the program. Maybe put it between World and Plots, so you can write down events and stuff directly inside that calendar, without going out.
For writing fantasy or sci-fi with weird calendars I like a feature like this, however as Manuskript is supposed to be a general purpose writing software, it might be one of the features, that will get in the way for all who don't use a calendar.
When I have a story with a heavy world building, I use Obsidian. It has a plugin for using The Fantasy Calendar, and it works very well.
@TheShadowOfHassen Well the possibility to add Metafields like I mention in #155 and then the possibility for Plugins, something like this here should be possible. Let Manuskript in the Core, all-purpose, but when needed, add a Plugin with the needed special functions!
I'm just planning a Comic and could find any solution which is working for me, so I will work on Paper, because I want to make a Storyboard, without a script. It's a try to perfect my one Storytelling, working more visual. I would like to do it in Manuskript and have the possibility to add Krita, for my Scribbles and a specialized View for it, but not possible at the moment for Manuskript!
I see this wish for such a Calendar in a similar scope, a cool Feature, for the people who need it, but also for a Majority, not so much!
That's my way of thinking. The possibility to add Metadata to text elements, is something which Manuskript is actual missing, when we have this, and a working plugin API, then someone could simply add an implemention of a calendar, if it is a normal one, or something completely fantastic, is then just a question, how to implement it! That is also the reason why I had referenced my own old Issue!
I hope what I mean and think is understandable!
In my opinion, adding a calendar generator on the navigation menu wouldn't be too much of a bother for people. I don't use the Outline, but it doesn't annoy me to have it there. Just my opinion though.
In the meantime, I created a code to add my own calendar in World. Just something simple.
It could be a useful alternative to the entry in the navigation menu.
Here is what it looks like:
This is the code I used:
day_names = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"] # names of the days of the week
x = len(day_names) # get the number of days in a week
month_names = ["Month 1", "Month 2", "Month 3", "Month 4", "Month 5", "Month 6",
"Month 7", "Month 8", "Month 9", "Month 10", "Month 11", "Month 12"] # names of the months
month_days = 30 # number of days in a month (all the same amount of days for now)
shift = 6 # which day of the week starts the year 0 = Monday, 6 = Sunday
s = shift # variable assign the days of the week to the days of the month
'''
Creating a fictional calendar. Its just for a single year.
@:param id: the ID of the last item created. Just create an item before doing this to see which is the last id in the world.opml file.
@:param year: the year you want for your calendar
'''
def calendar_year(id, year):
global s # global so it can work on every month, otherwise it would start from 0 each month
global i # creates global variable i to assign all ids to the calendar months and days
i = id + 1 # assign the ID to the global variable i incremented by 1
print(f' <outline name="Year {year}" ID="{i}">') # creates the year
for month in month_names: # creates months based on the month names you chose
i += 1 # adds 1 to the last id before assigning it to the month
print(f' <outline name="{month}" ID="{i}">') # creates the month
md = month_days
n = 1 # this is the day of the month
while md > 0: # loop to create the days of the month in the calendar
if s >= x: # this is to reset the days to 0 after reaching the last one or correct if shift is higher than the number of days
s -= x
continue
i += 1 # adds 1 to the last id before assigning it to the day
print(f' <outline name="{n} - {day_names[s]}" ID="{i}"/>') # creates the day in the format "Day_number - Day_of_the_week" for example: "25 - Monday"
n +=1
s += 1
md -= 1
print(f' </outline>') # closing tag for month
print(f' </outline>') # closing tag for year
if __name__ == '__main__':
calendar_year(5, 2024) # first argument is the ID, second argument is the year
I just copy-paste the output in the world.opml file. It just creates a single year and the months will be all of the same numbers of days. Parameter Id I take it from the last item created.
This is just a quick code I put up for making my own calendars. I have no idea how to add it to Manuskript. I'm not that good with coding.
I tried to add the moon phases. Can be toggled off by putting 0 in moon().
Here how it looks like:
I didn't know how to add the moon symbols but it can be easily inserted in the code.
Here's the code:
'''
This is how the lunar phases are written. Change the string to see different results on the day name.
'''
new_moon = "(----)"
waxing_crescent_moon = "(---|)"
first_quarter_half_moon = "(--||)"
waxing_gibbous_moon = "(-|||)"
full_moon = "(||||)"
waning_gibbous_moon = "(|||-)"
last_quarter_half_moon = "(||--)"
waning_crescent_moon = "(|---)"
waxing_moons = [new_moon, waxing_crescent_moon, first_quarter_half_moon, waxing_gibbous_moon]
waning_moons = [full_moon, waning_gibbous_moon, last_quarter_half_moon, waning_crescent_moon]
day_names = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"] # names of the days of the week
month_names = ["Month 1", "Month 2", "Month 3", "Month 4", "Month 5", "Month 6",
"Month 7", "Month 8", "Month 9", "Month 10", "Month 11", "Month 12"] # names of the months
x = len(day_names) # get the number of days in a week
month_days = 30 # number of days in a month (all the same amount of days for now)
moon_cycle = 0 # the number of days the moon takes to go from full to new
moon_phases_per_cycle = [] # how many times new_moon, full_moon, etc are repeated. It depends on the moon cycle
'''
This is the function to create the moon phases in the year.
@:param mc: The number of days the moon takes to go from new moon to full moon
'''
def moon (mc):
global moon_phases_per_cycle # made it global since it's used in the other function
global moon_cycle # same as above
moon_cycle = mc
divided = moon_cycle // 8 # finds out how many times a certain phase must be repeated
remaining = moon_cycle % 8 # finds out if there's days left to cover
waxing_number = remaining // 2 # assign half of the remaining days to the waxing moons
waning_number = remaining - waxing_number # the other half is assigned to the waning moons
for moons in waning_moons: # loop to assign the waning moons to the moon phases in the cycle
for n in range(divided):
moon_phases_per_cycle.append(moons)
if waning_number > 0: # this is the loop for the remaining moon phases
moon_phases_per_cycle.append(moons)
waning_number -= 1
for moons in waxing_moons: # loop to assign the waxing moons to the moon phases in the cycle
for n in range(divided):
moon_phases_per_cycle.append(moons)
if waxing_number > 0: # this is the loop for the remaining moon phases
moon_phases_per_cycle.append(moons)
waxing_number -= 1
'''
Creating a fictional calendar. Its just for a single year.
@:param id: The ID of the last item created. Just create an item before doing this to see which is the last id in the world.opml file.
@:param year: The year you want for your calendar
@:param day_shift: The day of the week the year starts on
@:param month_days: The number of days in a month. For now all months have the same number of days.
@:param moon_shift: Shifts the days of the moon phases
'''
def calendar_year(id, year, day_shift, month_days, moon_shift):
global i # creates global variable i to assign all ids to the calendar months and days
i = id + 1 # assign the id to the global variable i incremented by 1
mnsh = moon_shift
print(f' <outline name="Year {year}" ID="{i}">') # creates the year
for month in month_names: # creates months based on the month names you chose
i += 1 # adds 1 to the last id before assigning it to the month
print(f' <outline name="{month}" ID="{i}">') # creates the month
md = month_days
n = 1 # this is the day of the month
while md > 0: # loop to create the days of the month in the calendar
moon_phases = ""
if moon_cycle != 0:
while mnsh >= moon_cycle: # if you shift the moon cycle by too much this while loop corrects it
mnsh -= moon_cycle
moon_phases = moon_phases_per_cycle[mnsh]
if day_shift >= x: # this is to reset the days to 0 after reaching the last one or correct if shift is higher than the number of days
day_shift -= x
continue
i += 1 # adds 1 to the last id before assigning it to the day
print(f' <outline name="{n} - {day_names[day_shift]} '
f'{moon_phases}" ID="{i}"/>') # creates the day in the format "Day_number - Day_of_the_week" for example: "25 - Monday"
mnsh += 1
n +=1
day_shift += 1
md -= 1
print(f' </outline>') # closing tag for month
print(f' </outline>') # closing tag for year
if __name__ == '__main__':
moon(30) # the argument is the number of days it takes from full moon to new moon. If you write 0 it won't show the moon phases
calendar_year(5, 2024, 0, 30, 17) # first argument is the ID, second argument is the year, third is in which week day the year starts on, fourth the number of days in the months, fifth the shift in the moon phases
I agree with @obw, I think it's better as a plugin. Also, when the GTK port has plugins, I'll add it myself. I've already written a reasonably powerful fantasy calendar program in GTK.
It's fine, so long as it's not hard to work with it. Can't wait to use it. In the meantime, I'll make do with my messy code. xD
@FastusBellrune this mite be useful as in #934
Most problems with calendars and timestamps for metadata of your text files is that there is no solution which works for everyone. For example there could be differences in timezones between chapters. There could be different moon phases, multiple suns or different concepts of time calculation in a story. Especially when you enter science fiction with space ships which can escape a local planet the whole concept of calendars breaks down. But calculating time in general as portions of radioactive particles splitting (as physics does it) is very likely unpractical for many authors.
So even if we had a plugin for calendars, I would think that would need the ability to convert between multiple configurations.
But I personally also noticed calendars and absolute dates to be quite unpractical when you don't write a story with historic background. So calculating time relative might make sense in many cases.
However I still see huge issues for scenes where either your characters may travel through time or simply remember something of their past. Because then the timestamp for that scene might be set as the date from their memory or it might be set as the date they remember.
I also want to remind that even if you have a system which works for you. The chronological order might still differ from the narrative order for your story. Which implies that we would still need at least two different graphs showing the order of your scenes when we add a timeline that uses some kind of calendar/time system.
Don't get me wrong. If we end up with a plugin system in the end that gives most authors an option to add time information to their plot, that's great. But I want to point out why I don't think it's something which ends up being a core functionality of Manuskript.
This is a question, and maybe a future improvement.
Would it be possible to add a calendar generator inside the program?
Until now, I've been using donjon for this, and I copy the calendar in LibreOffice Calc.
It's useful to note down the dates of when stuff happens. Maybe it would be easier to add than adding the date to the timeline. It could be another entry in the navigation menu.