#pet: Your Personal Expenses Tracker

42 messages Β· Page 1 of 1 (latest)

hexed spruce
#

Hello everyone πŸ‘‹ so, sometime back I made a graphical program to help people in recording their daily expenses. It stores the expenses in a SQLite3 database and uses Nuklear for its UI
Recently I made QoL improvements to it but yk, with every project, without users, it vanishes,
So, the project is open source under the zlib license (similar to GLFW's)

https://codeberg.org/limisi/pet

Check it out and tell me whatchu think πŸ™ƒ

if you just want to have a feel of the UI you can check out the documentation of a previous version here
https://limisi.srht.site/docs/pet_v2_user_manual.html (includes screen shots πŸ™ƒ)

rn, I'm looking to add encryption and authentication 'cause its financial data so it should be secure by default, but I'd really like help with this πŸ˜„

other than that I'm working on being able to filter expenses by date range

finally, I need a system to enable people to add, edit or delete tags

so yeah, kindly do check it out and tell me what comes to you, I want as much scrutiny as possible on code quality 😀πŸ’ͺ do not hold back, I wish to improve

Also if you have ideas of how things can be done different, do tell me

Also, if you find any bugs/ inconsistencies 😀 let me at 'em 😀, they will be squashed (if my skill issues permit 😱)

hexed spruce
vernal junco
#

very nice!

hexed spruce
hexed spruce
#

Roadmap

  • Implement password, user authentication and partial encryption using monocypher for string encryption
  • write platform specific random number generation code to jumble prices when stored (unless a library already exists for this)
  • write out UI for tags and tags operations (add, edit and delete)
  • add analytics which allows you to see a graph of tags against money and can be filtered using dates
  • analytics: allow someone to see graph of how much they've spent on an item over a time period
#

With these down, a version 3.0 can be released

#

Analytics design mockup

#

Tags UI and new settings window mockup

hexed spruce
#

Got UI shifting to work 😁

hexed spruce
#

adding tags is now supported 😁

hexed spruce
#

Now supports editing tags 😁 (i.e updating and deleting)

mild flame
#

;compile -O2 -march=znver3 -mtune=znver3 -std=gnu23

#include <stdio.h>
int days_in_month (int y, int m)
{
    return (0x3f & 0x3bbeedc)
           + (((0x3bbeedc ^ (((y & 0x3) || !(y % 0x64)
           && (y % 0x190)) << 4)) >> (m << 1)) & 0x3);
}

int main(void) {
    printf("%d\n", days_in_month(1900, 2));
}
vestal tapirBOT
#
Program Output
28
mild flame
#

;compile -O2 -march=znver3 -mtune=znver3 -std=gnu23

#include <stdio.h>
int days_in_month (int y, int m)
{
    return (0x3f & 0x3bbeedc)
           + (((0x3bbeedc ^ (((y & 0x3) || !(y % 0x64)
           && (y % 0x190)) << 4)) >> (m << 1)) & 0x3);
}

int main(void) {
    printf("%d\n", days_in_month(2000, 2));
}
vestal tapirBOT
#
Program Output
29
mild flame
#

let me deobfuscate a bit

hexed spruce
#

However what makes it wrong though ?

mild flame
#

;compile -O2 -march=znver3 -mtune=znver3 -std=gnu23

#include <stdio.h>
int days_in_month (int year, int month)
{
    unsigned y = year;
    unsigned m = month;
    return 28U + (
        0x03U & (
            0x3bbeedcU ^ (
                ((y & 0x3U)  ||
                !(y % 100U)  &&
                 (y % 400U)) << 4U
            )
        ) >> (m << 1U)
    );
}

int main(void) {
    printf("%d\n%d\n%d\n%d\n%d\n%d\n%d\n%d\n%d\n%d\n%d\n%d\n",
           days_in_month(2000,  1), days_in_month(2000,  2), days_in_month(2000,  3),
           days_in_month(2000,  4), days_in_month(2000,  5), days_in_month(2000,  6),
           days_in_month(2000,  7), days_in_month(2000,  8), days_in_month(2000,  9),
           days_in_month(2000, 10), days_in_month(2000, 11), days_in_month(2000, 12));
}
vestal tapirBOT
#
Program Output
31
29
31
30
31
30
31
31
30
31
30
31
mild flame
#

hmm guess i didn't break it

mild flame
#

;compile -O2

#include <stdbool.h>
#include <stdio.h>
static int
days_in_month (unsigned y,
               unsigned m)
{
    return 28U + (
        0x03U & (
            0x3bbeedcU ^ (
                ((y & 0x3U)  ||
                !(y % 100U)  &&
                 (y % 400U)) << 4U
            )
        ) >> (m << 1U)
    );
}

static bool
date_is_valid (int year,
               int month,
               int day)
{
    return year >= 1 && month >= 1 && month <= 12 && day >= 1 &&
           day <= days_in_month((unsigned)year, (unsigned)month);
}

int main(void) {
    int d[] = {2024, 9, 20};
    printf("%d-%02d-%02d is %svalid\n", d[0], d[1], d[2],
           date_is_valid(d[0], d[1], d[2]) ? "" : "in");
}
vestal tapirBOT
#
Program Output
2024-09-20 is valid
hexed spruce
hexed spruce
#

That didn' cross my mind actually

mild flame
#

Btw feel free to use my totally self-documenting and not cursed implementation. It's the same exact formula but uses a lookup table where each month length info is a 2-bit field

#

Conveniently 0b11 == 3 == 31-28

#

So you can fit all 12 in 24 bits

#

;compile -O2

#include <stdbool.h>
#include <stdio.h>

static int
days_in_month (unsigned y,
               unsigned m)
{
    return (int)(28U + (
        0x03U & (
            0x3bbeedcU ^ (
                ((y & 0x3U)  ||
                !(y % 100U)  &&
                 (y % 400U)) << 4U
            )
        ) >> (m << 1U)
    ));
}

static bool
date_is_valid (int year,
               int month,
               int day)
{
    return year >= 1 && month >= 1 && month <= 12 && day >= 1 &&
           day <= days_in_month((unsigned)year, (unsigned)month);
}

int main(void) {
    int d[] = {2024, 9, 20};
    printf("%d-%02d-%02d is %svalid\n", d[0], d[1], d[2],
           date_is_valid(d[0], d[1], d[2]) ? "" : "in");
}
vestal tapirBOT
#
Program Output
2024-09-20 is valid
hexed spruce
#

I just documented the shid outta the codebase!

#

~4k new lines πŸ™‚β€β†•οΈ
courtesy of Gemini Clueless

devout fulcrum