devolution

Author Topic: Fun game, but I seem to have some issues with it..  (Read 35492 times)

0 Members and 3 Guests are viewing this topic.

Offline Xela

  • Global Moderator
  • *****
  • Posts: 6893
  • "It's like hunting cows"
Re: Fun game, but I seem to have some issues with it..
« Reply #15 on: October 10, 2016, 07:02:23 PM »
I don't remember and there is no way to tell from that data :( It's patched with some patches, that is for sure...
Like what we're doing?

Offline oratorio

  • Newbie
  • *
  • Posts: 7
Re: Fun game, but I seem to have some issues with it..
« Reply #16 on: October 10, 2016, 10:53:03 PM »
I don't remember and there is no way to tell from that data :( It's patched with some patches, that is for sure...


Devlog shows that it was run by someone named Adrian before it was zipped for transport.

Offline DarkTl

  • Hero Member
  • *****
  • Posts: 4737
Re: Fun game, but I seem to have some issues with it..
« Reply #17 on: October 11, 2016, 04:01:19 AM »
You have good ideas for balancing the game in the first post. But
At the same time, refinement should reduce the amount of dirt generated - more grace means less spilling...maybe? Or perhaps roll these two together into a single modifier for both fatigue and dirt.
In our case refinement is a knowledge about society and its customs and manners, not physical grace   :)

Offline Sarabada

  • Newbie
  • *
  • Posts: 30
Re: Fun game, but I seem to have some issues with it..
« Reply #18 on: October 11, 2016, 05:04:47 PM »
You have good ideas for balancing the game in the first post. ButIn our case refinement is a knowledge about society and its customs and manners, not physical grace   :)

Thanks for the input; Certainly that's a fair point, and if that is the case and intention of the 'purpose' of the game's refinement stat, then I'll agree that it shouldn't impact dirt generation, though I still feel that agility should help (It's really difficult to raise agility for slaves anyway since they are forbidden from participating in Combat Courses, and have to deal with very low success via Dance courses instead.)

The main reason I've been hesitant about going ahead with implementing any of my suggestions so far (and some of them are really easy, it looks like) is because anything I do would change the game's balance from what I assume was 'intended difficulty' you guys put out in the alpha. Anything I do would theoretically make it easier as guards and strippers level up faster, characters will be able to do a bit more / more effectively, taxes won't be so devastating (though I think if I do change it to hit net income instead of gross, I'll raise the lower level tax rates to still slow early growth a bit,) and so on. Part of my post was somewhat testing to see what anyone would've probably agreed on to be a good change to balance. Honestly, of the character/job-related changes, guards are probably my highest priority, because once you get to 1000 security rating, there is literally no reason at all to even field a guard team, much less have 5 of them in that little guard house.

Thus, I'm currently just doing UI/QoL improvements instead.

On that note, I tweaked my course assignment screen a bit more and fiddled with the colors again. I think I'm pretty happy with it now (wording could probably still change, though.) I decided to change the logic to include 3 'scenarios' instead of 2: Instead of the "days left" counter next to the girls showing the static/absolute end time of that course - which is reflected on the course's 'card' already anyway) I made it provide two different counters.

  • If a girl's already completed the course and gotten her bonus stats from it, it counts down to the absolute end day as normal, telling you how many more days she can continue participating in that class to get the regular bonuses, but making it clear she's already gotten the course bonus and won't be getting them again.
  • If a girl has not yet completed the course, the counter will instead display either the number of days left until she completes the course to gain her bonus stats, or turn red and count down to the absolute end day of the course if there's not enough time for the girl to get to that point.
I find this has given me a very easy way to very quickly and at a glance tell what the status of all the girls I'm training are. Important for me when I have 8 girls working to pay for the course cost, upkeep and wages of 14 other girls taking classes simultaneously. I've attached an updated screenshot showing all three statuses now.

With that out of the way, as I mentioned before, I'd like to ask if anyone could suggest a way to improve the code a bit - it works, but I'm really going in blind here, especially with no experience with Python nor any knowledge of the setup of this game's data structures (lots of guessing what data is available based on looking at similar sections of existing code, as well as the functions that define those structures. It's apparent to me just how much I was used to using my for k,v in pairs(t) do print(k,v) end loop in Lua to find the data available to me. Unfortunately, trying similar tactics here didn't go very well, because most things apparently aren't 'iterateable.' In short, I think there's probably more efficient methods of getting what I need, but the loops so far make logical sense to me.

Beginning with the course list name change to add in a numeric identifier, I altered this line of code:
The original:
Code: [Select]
text(u'{size=-5}%s'%course['action']) xalign 0.5The modified line:
Code: [Select]
text(u'{size=-6}%s %d%02d'%(course['action'], int(course['Teacher Skill'] / 10), int(course['Teacher Knowledge'] / 10))) xalign 0.5
Apparently I can't really set any variables in this file, because I kept getting errors/complaints that it expected only layout code, or something, so I had to call the data repeatedly in-line instead in order to handle the logic. Either way, the number is simply truncating the teacher skill and knowledge values and concatenating them together with the original course name to create a semi-sensible 'numbering system' where higher numbers = roughly better courses. In this case, since the range of values for creating a course are 30-100 skill and 40-300 knowledge, the 'worst' course would be a 304 course, while the 'best' would be a 1030 course. I also had to reduce the text size because it started overflowing with the extra numbers.

Now the big stuff is on the left hand 'summary' pane:
The original code:
Code: [Select]
                    for entry in [girl for girl in hero.girls if girl.location == "-PyTFall Educators-"]:
                        hbox:
                            vbox:
                                xmaximum 180
                                xfill True
                                text (u"{size=-2}%s:"%entry.name)

                            vbox:
                                text (u"{size=-2}%s"%entry.action)

The modified block:
Code: [Select]
                    for girl in hero.girls:
                        if girl.location == "-PyTFall Educators-":
                            for course in schools['-PyTFall Educators-'].active_courses:
                                if course['id'] == girl.mech_relay['courseid']:
                                    hbox:
                                        vbox:
                                            xmaximum 180
                                            xfill True
                                            text (u"{size=-3}%s:"%girl.name)

                                        vbox:
                                            #if girl has been in course longer than class completion length
                                            if int(course['chars'][str(girl)]) >= int(course['Duration'] * 0.7):
                                                text (u"{size=-4}{color=[royalblue]}%s %d%02d{/color} {color=[springgreen]}Completed!{/color} ({color=[firebrick]}%dd left{/color})"%(course['action'], int(course['Teacher Skill'] / 10), int(course['Teacher Knowledge'] / 10), int(course['Days Left'])))
                                            #if not long enough to complete, but enough time remaining to do so
                                            elif int((course['Duration'] * 0.7) - course['chars'][str(girl)]) <= int(course['Days Left']):
                                                text (u"{size=-4}{color=[skyblue]}%s %d%02d{/color} on Day {color=[lawngreen]}%d{/color} / {color=[gold]}%d{/color} ({color=[lightgreen]}%dd left{/color})"%(course['action'], int(course['Teacher Skill'] / 10), int(course['Teacher Knowledge'] / 10), int(course['chars'][str(girl)]), int(course['Duration'] * 0.7), int((course['Duration'] * 0.7) - course['chars'][str(girl)])))
                                            #if not long enough to complete, and not enough time to do so
                                            else
                                                text (u"{size=-4}{color=[darkslateblue]}%s %d%02d{/color} on Day {color=[lightcoral]}%d{/color} / {color=[goldenrod]}%d{/color} ({color=[red]}%dd left{/color})"%(course['action'], int(course['Teacher Skill'] / 10), int(course['Teacher Knowledge'] / 10), int(course['chars'][str(girl)]), int(course['Duration'] * 0.7), int(course['Days Left'])))

What's immediately apparent is that there appeared to be some shorthand occurring in the original code where it seems to be running multiple loops all at once in one line, but I have no idea how that worked, so I separated them into separate discrete loops instead. This would probably be where any optimization could come in, but as before, the bottom half looks like a nightmare because of my inability to define any variables in this file. Any suggestions, or is it basically fine as-is?

EDIT:
Somewhat unrelated, but if I will be training the girls I get from the slave market anyway, does it really matter what their work price and upkeep are? I ask because some are obviously more expensive than others there, but even going by the calculations in the code, I'm not coming up with the same upkeep costs, so I can't be sure that, all else being equal, two slaves bought at different starting costs would eventually come to have the same upkeep/work costs if I train them to make their stats identical to each other.

For example, there is a slave that has a work price of 49 and upkeep of 70, and another with a work price of 24 and upkeep of 75.

According to the code:
Code: [Select]
        def get_upkeep(self):
            if self.status == 'slave':
                if self.occupation == 'Prostitute':
                    bu = 20 * self.rank
                    su = self.charisma/10 + self.refinement*1.5 + self.constitution/5 + self.reputation/2 + self.fame/2 # Stats Upkeep
                    ssu = self.anal/8 + self.normalsex/8 + self.blowjob/8 + self.lesbian/8
                   
                    return int(bu + su + ssu + self.upkeep)

They are both rank 1, so that's a base of 20. The first one has 5 Charisma, 10 Refinement, 40 Constitution, 17 Reputation, 12 Fame, and 21/17/18/21 of the relevant skills.
The second one has 29 Charisma, 0 Refinement, 40 Constitution, 0 Reputation, 0 Fame, and 0/0/0/0 of the relevant skills.

Based on these stats, I would naturally prefer the first one, but I wanted to see if the price disparity still exists when they are trained up. Unfortunately, the base numbers don't match.

The first one would have upkeep of:
20 + 5/10 + 10*1.5 + 40/8 + 17/2 + 12/2 + 21/8 + 17/8 +18/8 + 21/8 = 64.625, or 64 gold, where the game claims she has an upkeep of 70.
The second one would have upkeep of:
20 + 29/10 + 0*1.5 + 40/8 + 0/2 + 0/2 + 0/8 + 0/8 + 0/8 + 0/8 = 27.9, or 27 gold, but the game says she has upkeep of 75! Granted, I don't know what value self.upkeep contains, but I can't be sure if it makes that large a difference, especially between the two girls.

The gist of it all is that I have no idea if I should be hiring these slaves hoping for the upkeep to not be insane later on. In the second slave's case, it would be a nightmare if I trained her up and her upkeep still ends up being triple her work price.
« Last Edit: October 11, 2016, 05:50:57 PM by Sarabada »

Offline Xela

  • Global Moderator
  • *****
  • Posts: 6893
  • "It's like hunting cows"
Re: Fun game, but I seem to have some issues with it..
« Reply #19 on: October 11, 2016, 09:15:15 PM »
Upkeep should be less of a burden for well developed character. Those number might be off because numbers are not floats, in python:

Code: [Select]
>>> 1/2
0
>>> 3/2
1
>>>

integer division is not behaving as you'd expect unless converted to floats first. self.upkeep is usually modified by traits.

You GUI code seems fine, you can use interim variables in screen code through python blocks or oneliners:

Code: [Select]
python:
    knowledge = int(course['Teacher Knowledge'] / 10)

$ days_left = int(course['Days Left']

You can iterate over all containers in python just like in lua, you can write to log/raise exceptions or view data structures through console. Printing to cmd is not very easy to setup.
Like what we're doing?

Offline Sarabada

  • Newbie
  • *
  • Posts: 30
Re: Fun game, but I seem to have some issues with it..
« Reply #20 on: October 12, 2016, 01:13:48 AM »
Right, upkeep is less painful once the character gets 3-4 AP and can pay for themselves and charge higher prices, but I was trying to figure out how to tell which slaves were and were not worth it to purchase and train up - for my previous example, I'm not sure if the second 24/75 slave would in the end be equal with the 49/70 slave, or if the 24/75 girl will always have a much higher upkeep than her work price even at higher stats. I feel like I suck at trying to explain what I mean, but I'll try to look into their traits to see which ones modify their costs, assuming they're in the *.rpy files I'm poking through.

I had thought that the results of division would be floats naturally unless explicitly converted to ints, but if they are converted to ints at each step, that would result in more zeroes and such being added, which would make the resulting upkeep value even less than the stated value.

As far as my GUI code goes, thanks for looking it over; I'm glad to know it's fine for a first attempt. Could you elaborate a bit on what you mean by the python bit, or more specifics on the syntax? Are you saying that I can define variables in a python block and then use those variables once I'm 'out' of the block? I don't know if you can use those color codes inside python code itself.

Also, I feel like I stumbled into a bug with the course assignments system, largely because I'm looking at it so closely right now making sure the code I've written is bug-free. Normally, when the course's "Days Left" counter hits 0 or less, a function in the base code prints a message that the course ended, and then removes it from the list, and for the most part, this worked even though I was a bit confused about getting 1 more day of stats out of it on the last day (0 days left.)

However, I just ran into a situation where it ticked down into -1 days left, and I got yet another day of stats out of the course somehow. Thinking it was something with my code, I reverted the game back to fully stock code by restoring copies of the original library files, and the issue persisted: The course went from 0 to -1 days left, but continued to function. My biggest hypothesis is that on the day the code was supposed to remove this course a bunch of my girls 'finished' another course, and the code cycled through the first function to tell me that they all completed a course and got bonus stats (still had days left before that course itself expired,) but then for some reason ended up failing to run the second part of the code to remove the course that should have already expired. I couldn't figure out why that would happen because it doesn't make any sense to me that one function would run and not another. I decided to try and go one more day beyond that (when the course was listed at -1 days left) and it was finally removed on the following day.

I... have no idea what happened or why, nor any idea how to go about fixing that. I do have a save file to reproduce this 'timing' of courses ending, in the unlikely event anyone actually wants to try looking into it, but as far as I can tell, it has nothing to do with my code.

Offline DarkTl

  • Hero Member
  • *****
  • Posts: 4737
Re: Fun game, but I seem to have some issues with it..
« Reply #21 on: October 12, 2016, 12:54:46 PM »
We have a preliminary concept for slaves and slave training. The idea is based on Xela's favorite Ancient Rome, where skills were the most important quality of a slave.

 For example, there is a semi hidden striptease skill, important for corresponding job, which goes from 0 to infinity, and one can raise it by 1-2 per day at best. Alpha doesn't have skills, but they already exist in the dev version.
Meanwhile to be considered as a really good stripper character needs skill at least 1000. So you can buy super cheap slave with zero skills and spend 2000 turns to make her a perfect stripper, or you can buy a very expensive slave which will get you high income due to high skills.

The courses code was completely rewritten after the alpha (it was in a truly poor condition back then). I admit I never used courses much though, I prefer using items.
« Last Edit: October 12, 2016, 01:09:35 PM by DarkTl »

Offline Sarabada

  • Newbie
  • *
  • Posts: 30
Re: Fun game, but I seem to have some issues with it..
« Reply #22 on: October 13, 2016, 04:59:25 PM »
Thanks for the insight, Dark. personally, I am very much against 'hidden' modifiers, even if they do make sense, simply because as a player, not knowing the numbers and effects hampers my ability to make effective and efficient decisions, but perhaps that's just me. Part of my modding right now is to expose more information, after all, and I've managed to get each girl's 'fame' value showing now. It irked me for a while because the code is clearly taking it into account for various things, yet this number wasn't visible anywhere, so I couldn't calculate anything. Same thing I'm running into now with any traits that may impact upkeep costs (I still haven't had much success with this particular search.)

Still, it sounds like what you are suggesting is that in the end the two girls in your hypothetical stripper scenario could be the same if you get their skills to align with each other (all else being equal.) My concern here was that there was nothing I could use to tell me if the two girls would eventually become 'equal' or if the second slave girl would always be 'worse' simply because they started that way.

Anyway, I found some examples of declaring variables in-line using the $ syntax in the code, so I'll be studying them to see how I can utilize them, if nothing else, to help clean up my code a bit. However, I still have no idea how to write to the logs, view data through a console (what console?) or if these require some sort of dev/debug mode, how to enable such.

On the point of the course code, I assume you mean you're not surprised there are these 'timing' bugs with it as it was 'a mess.' I'm not totally surprised either, especially since as I'm highlighting information to make them more easily recognizable, I'm also noticing due to it that the whole "customer chooses girl with X trait" stuff is kind of broken, too. Specifically, the customer will appear to check that any girl has a specific trait they desire and still has AP to act, but then if it finds a match, it just goes with a random girl anyway. In effect, because some girl had 'tough' and available AP, customer decided to "do it" with a girl who didn't actually have 'tough,' but actually had 'fragile' instead, which I found amusing. If the customer wanted 'meek' and the only girl with 'meek' already ran out of AP, then it sensibly chose a random girl, but the 'match but random anyway' logic is amusing.

I personally do use courses often though, for two reasons:
  • Items won't be able to keep your girls maxed out in specific stats once they level up a good amount, and it's cheaper to use courses to give them that initial boost to 30 or 50 or 80 before applying items on top.
  • Something I want to try and address as well, most of the relevant skills used by a job aren't actually increased naturally by doing said job.
    • Prostitution relies on sex skills, constitution, refinement and charisma, but it naturally raises all of them (with room upgrades at least) except for charisma.
    • Service girls rely on charisma, service and agility, but service is the only stat it raises naturally.
    • I think strippers are the only ones who get all their relevant stats raised just by performing - charisma, striptease and agility.
    • I suppose guards technically do too, but they are more or less useless at 1000 security rating, so it doesn't matter.
At this point, I think I may start trying to add in some of the balance-impacting modifications I suggested in my OP. I'm in a pretty comfortable spot right now, generating 295k gross income with a total weekly net profit of 55k a week without doing any arenas anymore (been going around preparing all the free girls for the next hiring spree to move to the second mansion/palace.) This is with a bunch of girls still being trained in the academy, so there's still some drain and they're not producing any income. I guess I more or less feel like I've 'beaten' the game now as it was intended, as I'm generating enough profit to get everything else I need at a decent pace. The utter uselessness of the guards is also really starting to bug me - I'll probably make it so that even at 1000 security rating, it's not a 100% defense against aggressive customer events.

I did run one more calculation similar to my OP with my current financial situation, and the gist of it is that if I were to exempt both wages and upkeep right now, I'd go from +55k/week to +92k/week, about a 37k/week difference, which doesn't sound all that bad considering the 30k everyone wants to charge for training right now. If I only exempt wages, then it's only an extra 16k/week for a total of 71k/week, and if I only exempt upkeep, it'd be an extra 21k/week for a total of 76k/week.

Before that, though, I have a few more UI-related tweaks I want to do, and one of them is to make it more readily apparent/easily visible when a girl has leveled up.
To do this, I modified the nextday screen to search for the 'level' information, and if the girl leveled up, to put it in the first line.

However.. I don't know why this line gives me an error: (Some sort of key error?)
Code: [Select]
if event.girlmod["level"] > 0:But, somehow, this works fine:
Code: [Select]
for key in event.girlmod:
    if event.girlmod[key] > 0 and key == "level":
Why does it seem to necessitate looping through all the keys instead of just letting me query the value directly?
« Last Edit: October 13, 2016, 05:05:22 PM by Sarabada »

Offline Xela

  • Global Moderator
  • *****
  • Posts: 6893
  • "It's like hunting cows"
Re: Fun game, but I seem to have some issues with it..
« Reply #23 on: October 13, 2016, 07:18:30 PM »
Do we log levels to girlmod???

If we do, safer code would be:

Code: [Select]
if event.girlmod.get("level", 0):
    # do something

But if we do not, even if it doesn't throw errors, it will not ever return anything meaningful.
Like what we're doing?

Offline Sarabada

  • Newbie
  • *
  • Posts: 30
Re: Fun game, but I seem to have some issues with it..
« Reply #24 on: October 13, 2016, 07:34:33 PM »
I'm under the assumption that it does, but I obviously have no way to say so definitively because there are still immense parts of the code I don't yet understand.

But, during the screen where it displays a summary of each girl's specific stats gained and lost, it will show "Level : 1" in the event that she has leveled up (in which case you'd also often see a 'green' number listed for Fatigue, as she would have fully restored her stamina on the level up.)

The stock code for that summarization is this:
Code: [Select]
for key in event.girlmod:
    if event.girlmod[key] != 0:
        hbox:
            hbox:
                xmaximum 150
                xfill True
                text (u"{size=-3}%s:"%key.capitalize())
            hbox:
                if event.girlmod[key] > 0:
                    if key == "fatigue":
                        text (u"{size=-3}{color=[red]}%d"%event.girlmod[key])
                    else:   
                        text (u"{size=-3}{color=[lawngreen]}%d"%event.girlmod[key])
                else:
                    if key == "fatigue":
                        text (u"{size=-3}{color=[lawngreen]}%d"%event.girlmod[key])
                    else:   
                        text (u"{size=-3}{color=[red]}%d"%event.girlmod[key])

Nothing there singles out the "Level" line, so I assumed that it was listed along with all the other stats in event.girlmod (rather, "level" must be one of the 'keys' it printed with capitalization.) This also explains why the level gained line was never on its own, but mixed in somewhere in the middle of the list, which is why I am trying to pick it out and put it on the first line to begin with.

My edit is simply:
Code: [Select]
for key in event.girlmod:
    if event.girlmod[key] > 0 and key == "level":
        hbox:
            text (u"{size=-1}{color=[springgreen]}Level Up!{/color}")
for key in event.girlmod:
    if event.girlmod[key] != 0 and key != "level":
        hbox:
            hbox:
                xmaximum 150
                xfill True
                text (u"{size=-3}%s:"%key.capitalize())
            hbox:
                if event.girlmod[key] > 0:
                    if key == "fatigue":
                        text (u"{size=-3}{color=[red]}%d"%event.girlmod[key])
                    else:   
                        text (u"{size=-3}{color=[lawngreen]}%d"%event.girlmod[key])
                else:
                    if key == "fatigue":
                        text (u"{size=-3}{color=[lawngreen]}%d"%event.girlmod[key])
                    else:   
                        text (u"{size=-3}{color=[red]}%d"%event.girlmod[key])

Could you explain what makes that bit of code you posted 'safer' and whether I should try to apply that change to the original loop? As well, I'm trying to check if it is greater than zero, but I don't understand if event.girlmod.get("level", 0) would return a zero value, or the value it actually holds. Finally, what is the error/issue with trying to address it the way I did the first time (and ran into errors as a result?)

Offline Xela

  • Global Moderator
  • *****
  • Posts: 6893
  • "It's like hunting cows"
Re: Fun game, but I seem to have some issues with it..
« Reply #25 on: October 13, 2016, 10:03:07 PM »
Could you explain what makes that bit of code you posted 'safer' and whether I should try to apply that change to the original loop? As well, I'm trying to check if it is greater than zero, but I don't understand if event.girlmod.get("level", 0) would return a zero value, or the value it actually holds. Finally, what is the error/issue with trying to address it the way I did the first time (and ran into errors as a result?)

Since you do not know for sure that level is in the dict, it's not safe address it directly, dict.get() checks if there is a key and returns a 0 if there isn't without raising exceptions.

Modern code would be something like:

Code: [Select]
vbox:
    if event.girlmod.get("level", 0): # Places level first and does nothing if level was unchanged.
        fixed:
            xsize 150
            text "Level:" xalign .0 size 17
            text event.girlmod["level"] xalign 1.0 size 17
           
    for key, value in event.girlmod.iteritems(): # Places everything else:
        if key != "level" and value:
            if key == "fatigue":
                $ color = red if value > 0 else lawngreen
            else:
                $ color = lawngreen if value > 0 else red
            $ key = key.capitalize()
            fixed:
                xsize 150
                text "[key]" xalign .0 size 17
                text "[value]" xalign 1.0 size 17 color color

which would have placed level first without colors and everything else after with proper colors. I cannot check if this works though :( I don't even remember if xsize was a thing back then or you still had to set xmaximum and minimum to that amount...
Like what we're doing?

Offline oratorio

  • Newbie
  • *
  • Posts: 7
Re: Fun game, but I seem to have some issues with it..
« Reply #26 on: October 13, 2016, 10:11:18 PM »
Using your first method (if statement), if girlmod only has entries for those things that have changed, the check would return an error for any girl that didn't change level because the key doesn't exist while the loop would just never find the key. If girlmod is populated with all of the possible changes, they should both work as far as I can see, but then I'm only a very out of practice programmer and I only know this code slightly.

Offline DarkTl

  • Hero Member
  • *****
  • Posts: 4737
Re: Fun game, but I seem to have some issues with it..
« Reply #27 on: October 14, 2016, 12:43:23 PM »
Thanks for the insight, Dark. personally, I am very much against 'hidden' modifiers, even if they do make sense, simply because as a player, not knowing the numbers and effects hampers my ability to make effective and efficient decisions, but perhaps that's just me.
They will be semi hidden. Like, we won't show raw numbers, but will show for example progress bars of some kind without numbers to give a general idea what the character knows already.
Skills consist of theoretical and practical parts and also have various modifiers, so showing raw numbers in gui will only lead to information overload.

Quote
Same thing I'm running into now with any traits that may impact upkeep costs (I still haven't had much success with this particular search.)
Well, traits files are in game/content/db if you want to check upkeep values. I don't really remember how many traits files we had in alpha, there could be only one.

Do you think it should be visible? I mean, traits upkeep changes are flat and small, if some trait gives +50 you wouldn't even notice it when you make 50K per week.

Still, it sounds like what you are suggesting is that in the end the two girls in your hypothetical stripper scenario could be the same if you get their skills to align with each other (all else being equal.) My concern here was that there was nothing I could use to tell me if the two girls would eventually become 'equal' or if the second slave girl would always be 'worse' simply because they started that way.
In the dev version small characters have permanent evasion bonus, while athletic ones have bonus to max health and vitality. Which one is the best? That depends on what you think is the best. Any trait is useful in some cases and not so useful in others.

And all skills (not stats, like charisma, but skills, like stripping) could be mastered by anyone, given enough time. Although some traits speed up the learning process for some skills, but not much.


Offline Sarabada

  • Newbie
  • *
  • Posts: 30
Re: Fun game, but I seem to have some issues with it..
« Reply #28 on: October 20, 2016, 02:21:00 AM »
Apologies for the delayed response; It's been a very busy weekend here. Haven't had time to do anything until now.

To respond to everyone who has posted:

@Xela and @oratorio,
Thanks for the explanations, I understand what the issue is now. My error stems from the fact that I became way too comfortable with how Lua handles these events - specifically, in this situation, if I try to address a value that doesn't exist, Lua simply returns its value as nil. Normally I do check that a value exists in Lua (very simply with if x and x > 3 then ...) before doing anything with it, but in the event that I forget, Lua's error message would helpfully state "attempt to compare number with nil" to let me know the reason, but Python's key error message was a bit more cryptic for me. I also had no idea if similar syntax would work in Python, but that's probably something I should look up.

As to your updated code snippet, I'll try to decipher it and put it in if it works more efficiently, but I think as long as my edited code works fine I'll probably leave it alone - it's not worth the effort right now to try and overhaul old code when I'm only interested in adding a couple QoL features for myself. The syntax would also be quite different from the rest of the alpha's code.

@Dark
Progress bars will probably be okay, as long as the information is visible somewhere - I'd argue for numbers instead or in addition, though, if it was a stat that you needed to monitor closely. I guess I'm just more of a numbers person, haha. I would say that providing numbers and modifiers for skills would not necessarily result in information overload if done well. I have an example to provide which I'll go over momentarily.

Thanks for the tip on the traits file - I was looking through the *.rpy files, so I overlooked the db files. I pulled it up and the trait upkeep (along with the int() rounding) accounts for all the differences I saw, so I can properly calculate income vs upkeep now. It also supports my suspicion that the 'Cute' trait is broken -- it's not even listed in the traits file, so the Bunny Slippers item never had any effect trying to grant the 'Cute' trait.

As for whether or not they should be visible, I'm biased, but I still argue for including it -- perhaps you can have an option to toggle on 'verbose' information to include numbers, but it wasn't until I looked into the traits file before I understood what the difference between, for example, "Tough" and "Athletic" was, which could influence which girls I wanted to hire, and confirmed my suspicion that "Fragile" indeed reduced a girl's maximum Fatigue value; Sure, I saw this in-game because it's a very visible stat, but I could only guess at something that made sense. However, then you have 'Hyperactive' which also reduces maximum Fatigue for some reason, but I wouldn't have guessed that.

Lack of information regarding girls' 'effects' is also something I take issue with - Sakuya has "Composure," but unlike hovering over her traits, hovering over the 'Composure' effect tells me exactly nothing, because there is no on-hover tooltip like with the traits (even then, it's just a vague description..) I had to resort to searching through the code to find out that it keeps the girl's 'Joy' within a set range, or rather that it grants or deducts 1 Joy each day until it reaches 60. If this effect would be too cumbersome to explain in such detail, it could be more simply stated as "This girl's mood is relatively stable, resisting being overjoyed or depressed." or something similar to that extent.

As for the dev version's various bonuses, I do hope they are detailed somewhere. Sure, smaller characters having bonus evasion could theoretically make some sense, but I don't know how much "sense" people put into that, versus a character with high "agility" that people naturally equate with higher evasion. The other problem is that I'm not sure the same level of 'attention to detail' would be placed on other facets of the game, thus causing inconsistency - having players realize mechanics and bonuses/penalties through context requires consistency.

As for skill mastery, that's fine, I was mainly trying to see if there would be a case where slave X has absolutely no chance to ever match slave Y simply because they started off differently.

---------------------------

Phew, okay, moving on.

As I mentioned, I didn't have much time to do anything this weekend due to being busy, but I finally had some time today to play again, and so I decided to whip up another edit/addition to another area I had immense frustration with - the "Girl List" screen. I assume it was meant to be an overview screen, but it told me very little about how my girls were actually doing, to the point where I had to manually go in and open up the profile screens of each and every single girl every turn anyway.

The stock screen provided information on the class, status, location, action and AP of each girl, but there was more information I needed to check each girl daily for. The most important was their Fatigue level - I need to know who is on the verge of tiring out so I can adjust the girls' orders accordingly. Other data I would glance over was their experience gain, to see if I could judge whether or not they could get away with continuing to run their job without rest until their next level-up. As well, for the Prostitutes, since I trained 20 of them simultaneously, I had a hard time remembering who managed to hit what rank, and ended up having to cycle through all their profile pages repeatedly. All of this meant that the overview screen was basically useless to me because I was forced to go in the profile screen anyway.

However, with my edit, I ended up exposing a lot of information - Much more than was available by default. While I could technically pare it down by removing some pieces of information (things like HP and MP don't change for 98% of my girls) I decided to go with another method, and what I was referring to Dark above: Utilizing colors, as I have done for other information-dense screens so far.

To start off with, I increased the size of the name bars/buttons to make them more visible and apparent that each is a new block. Within each, the bulk of information is more or less the same color -- HP, MP, Joy, Disposition, and Location should be green, as that signifies everything is normal. In this way, I can glance at the middle of every block and see if any girl is having issues.

At the same time, I decided to "color code" the four main jobs, and give their appropriate jobs the same color. This lets me tell at a glance who is doing what very quickly, and also shows me if I've (accidentally or intentionally) given a job to a girl who isn't equipped for it - In the first screenshot, Retsu will complain if I ended the turn because she's doing a green task when she's a pink class. For Prostitutes, I also added their rank next to their class so I can simply scroll through the list to see who needs catching up.

When a girl is sent to a class, both the location and the course appear in blue, letting me know they're busy doing something else (and if I want more detailed information about the course, I go into the course list screen that I edited some time last week.)

Negative statuses appear in bright red, which is very visible against the more muted colors everything else uses, so there's no way I can miss Kasinda having nothing to do and nowhere to go. Nami in the second screenshot also has nothing to do, but she at least has her own place to stay in, being a free girl, so it's not quite as high a priority as sorting out Kasinda's situation, so her location is only pink.

I've also color coded the AP numbers, mainly so I know who has 4+ AP and who still needs more constitution training. AP of 1 or 0 are red.

Resting I have two colors for, mainly because I consider "AutoRest" a slightly negative detail, as that means you've pushed the girl too hard

Finally, the biggest thing I need to check every turn, the Fatigue value. If a girl has exceeded 75% of her maximum Fatigue level, it turns red, but otherwise, I can very easily scroll through and see if anyone is over 200~250 without having to go in and wade through all 50 girls' profile pages every turn. Experience is included because why not; As I said, I do check it anyway to gauge if they can get away with not resting.

Honestly, the most useful application is for checking my service girls, as shown in the third screenshot -- I have to set them to work in shifts, because of how much fatigue they gain serving a stripper's clients, and this makes it very easy for me to tell who is ready for the next shift.

I'm quite happy with the information I've exposed, and although there's a lot for you to dig into, on a turn-by-turn basis, I really only check for the color of Fatigue and whether their class and job colors match. Additionally, I went in and edited the profile pages again to use similar job/location/class colors for consistency. I couldn't use the same colors, though, since the background is such a shade of yellow that most of the lighter colors are impossible to see on it. That said, I now generally only need to go into the profile screen if I want to interact with the girl somehow (change action, send to training, etc.) or check their detailed stats and equipment.

I also added a new element to the top of the screen, since there's some extra vertical room anyway from the screen being limited to 4 rows of girls per page. I added a message that tells me how many girls are matched on the current filter settings - it's a small detail that I personally like to have.

As an aside, it's pretty damn sad that my third girl, Karen-the-self-stabbing-guard is still only level 13 after guarding for 2 years, while Nancy, the Prostitute I didn't hire until the 4th house and then spent forever training through various courses, is already level 169. She can, based on stats, literally take on and destroy my entire 5-person guard team right now on her own.

In doing all this, I've been playing around with the '$' syntax to use variables in these 'screen' pages, which has worked out very well - thanks for pointing me toward that, Xela!
I still am wondering how to print stuff to logs that was suggested, though. Is it as simple as inserting
Code: [Select]
devlog.info("number of clients is %d"%int(len(self.clients)))somewhere within the code where self.clients is defined?

Edit:
One other annoying bug is that I accidentally equipped Alice with two Rods (Archmage Staff and Wand of Concentration) and now I can't remove them because both used RodAttack, but removing one automatically removes RodAttack because the code doesn't check for duplicates or anything else that still uses RodAttack. This, if I remove one Rod, the other one cannot be removed because there's no "RodAttack" left to remove. Unfortunately, I'm too lazy to go fix that piece of logic since it involves a lot more lookup of other functions I'm not familiar with yet.
« Last Edit: October 20, 2016, 02:32:27 AM by Sarabada »

Offline DarkTl

  • Hero Member
  • *****
  • Posts: 4737
Re: Fun game, but I seem to have some issues with it..
« Reply #29 on: October 20, 2016, 10:38:33 AM »
It also supports my suspicion that the 'Cute' trait is broken -- it's not even listed in the traits file, so the Bunny Slippers item never had any effect trying to grant the 'Cute' trait.
Yeap, it's a legacy trait from WM which we removed after a small discussion, but its traces still remained in alpha. The problem with such vague traits is their high subjectivity, an item could be cute or not cute for different people. Same for characters, some people find a specific character cute while others don't.

However, then you have 'Hyperactive' which also reduces maximum Fatigue for some reason, but I wouldn't have guessed that.
I believe the idea was that Hyperactive ones waste part of their energy on unnecessary movements  :)
However, traits can be freely and easily edited by player, that's why they all are in a separate file with rather simple syntax.

Sure, smaller characters having bonus evasion could theoretically make some sense, but I don't know how much "sense" people put into that, versus a character with high "agility" that people naturally equate with higher evasion.
Agility grants evasion too. It just means that with the same agility level a small character will have more chances to evade due to small hitbox.

Lack of information regarding girls' 'effects' is also something I take issue with - Sakuya has "Composure," but unlike hovering over her traits, hovering over the 'Composure' effect tells me exactly nothing
Xela likes when games have a few hidden mechanics without clear descriptions which could be understood only by playing the game.

The other problem is that I'm not sure the same level of 'attention to detail' would be placed on other facets of the game, thus causing inconsistency
I'd like to think that we'll have more than enough attention to details eventually  :D

One other annoying bug is that I accidentally equipped Alice with two Rods (Archmage Staff and Wand of Concentration) and now I can't remove them because both used RodAttack, but removing one automatically removes RodAttack because the code doesn't check for duplicates or anything else that still uses RodAttack.
Nice catch. Although, we decided to simplify the system and equip all weapons which give new attack skills to the right hand slot, because it quickly became messy once we added a few dozens battle skills for weapons.