UPDATE: still bad at social media.

edgeofinnerspace's Avatar

edgeofinnerspace

13 Apr, 2023 10:51 PM

or more correctly social media is bad for me. but on top of the head injuries i tend to forget to check my email even... for weeks sometimes.

i have a few questions about nodebox still. tweaking my 'knots' can become obsessive without an end it sight most of the time. but here is a design i think im going to use in my collection. i've also included a proof of concept piece i'm going to use for ...*whispers* ˢᵒᶜᶦᵃˡ ᵐᵉᵈᶦᵃ.

but it seems to take a bit of time to render each time i make changes to a design with this current node flow. im sure there is a much more efficient way to do all this because... yes, im still doing it my way. Wilson's are known for their stubbornness what can i say. plus i have trouble following some of your suggestions in the other post john.

also, i keep trying to approach this program, or the concept of ports maybe, with a feeling that there is a step somewhere down the line where the end-user, myself in this case, interacts with a single or a small group of nodes, or possibly some type of interface that applies the interaction globally. i worded this badly, but i think it goes back to the variables concept we touched on. or is this possibly something (what i tried explaining and also variables) that can be achieved by publishing root network ports? and if not, im very curious what the purpose of that is. there had to have been some intention behind it right? or was it just possible because it is possible in the subnetworks?

some other thoughts:
- im trying to figure out a way to adjust a length or angle from the "last point" while maintaining the first. i had some thoughts, but by the time i think them through to something that seems like it might work i seem to forget them too.
-similarly, and this may go back to the variables thing: is there a way to have all matching length inputs be changed from the same instance?
- is there a way to show the grid as well as the knot without it running through the combine and copy at the end? also, why does the alt_grid give an error when it passes through a colorize? or maybe its the combine node?
- and lastly for now, is there a more efficient way to achieve this setup to reduce render time? or it just the number or calculations happening - maybe thats redundant...

i think in the end im still approaching this in the way i am is just because i havent learned much about the program and its currenty the easestfor me to retain from day to day.

  1. 1 Posted by edgeofinnerspac... on 15 Apr, 2023 01:26 AM

    edgeofinnerspace's Avatar

    quick question but not sure it deserves another post.

    how can 'wrap' a typical sine wave around an origin? im guessing as some variation of a radius of a circle. but i've tired the wave node and i just cant quite work it out. anyways, its unrelated to kryptoknots but a test project im using to help me figure out some concepts used in the launching of the knots collection.

  2. Support Staff 2 Posted by john on 16 Apr, 2023 12:53 AM

    john's Avatar

    I will answer your last question first.

    Nodebox didn't have a single node that would cleanly wrap a sine wave around a circle, so I made one for you:

    http://support.nodebox.net/discussions/show-your-work/586-circle_wa...

    Demo with circle_wave node attached to that link.

    Enjoy! I'm eager to see what you will do with this,

    John

  3. Support Staff 3 Posted by john on 23 Apr, 2023 09:40 AM

    john's Avatar

    Edgeofinnerspace,

    I realize I never answered your earlier post. My apologies...

    I was also puzzled why your render time was so slow, so I examined your code. The reason was buried deep inside your latestLine nodes. You had a subnetwork called choseLength to calculate the length of each line segment based on length input and whether the angle was odd or even. To make this calculation you created TWO large alt_grids of 33 columns and 29 rows each - a combined total of 1882 points. You then sorted these grids, sliced two points from each, and took the distance between those two points.

    That was a lot of work to find a single number. And you repeated that for each line segment in the drawing. That's what was slowing you down.

    Turns out there is a much easier way. If the angle is odd, your length is just the supplied length times 10 (your scaling factor). If the angle is odd, the length is just that value times the square root of 3. (This is the geometry of isometric grids.). So there is no need to make those large grids and sort them each time.

    I went ahead and replaced your latestLine nodes with an improved version that replaces the inefficient choseLength subnetwork. I also isolated the endpoints of the previous segment INSIDE the latestLine node so that you don't have to keep placing a points node outside each copy. At the bottom I changed it slightly: you only have to do the 3-way rotation once, not twice. Other than that, I am still using your same approach.

    See demo and screenshot (attached). Your old network is on the right; my version is the column on the left. The drawing now renders almost instantly.

    I will answer all your other questions in a separate note.

    John

  4. Support Staff 4 Posted by john on 23 Apr, 2023 11:05 AM

    john's Avatar

    Edgeofinnerspace,

    Your remaining questions...

    Is there some way of sneaking in global variables?

    No, there is not. If you need a value for a node or subnetwork, you will need to directly feed it in from above. This is sometimes a royal pain, but it has many advantages. And there are ways to reduce the pain (see below).

    Could you achieve global variables by publishing root network ports? If not, what is the purpose of that?

    Publishing ports at the root level allows you to create a top level parameter pane that could make it easier to change values fed into top level nodes. So if you had several nodes at the top of your root level with values that affected everything below, you could adjust the final output by selecting each of those nodes and changing the key values. OR you could publish them and then change those values in the parameter pane.

    This would work in exactly the same way, but by publishing and using the parameter pane you could change all the key settings in one place without having to find the individual nodes each setting was defined in. I rarely use this option, but it would be nice in situations where you frequently want to adjust the final output with multiple settings. But those settings still need to filter down your network, so this does not provide a magic way of achieving global variables.

    How can I adjust values from the last point while maintaining the first?

    I'm afraid I don't understand this question. Your current method chains together all your segments using relative angles, so any change to one segment will affect everything below it.

    There is an alternative to chaining, which I mentioned earlier in our discussion. Instead of using relative angles, you can use absolute angles: multiples of 30 degrees that remain fixed regardless of the angle of the previous segment. There is no need to calculate starting points either: all segments start at the origin. Then, to make your drawing, you simply combine them in order and join them using my join node with the new "End-to-End" option.

    With this system you can change any single line segment without causing angle changes downstream. I think it also makes the angles easier to calculate: you can just look at the direction of each segment from a paper sketch without having to add or subtract from the previous segment's direction. This is the system which I proposed earlier, but which you are resisting due to "Wilson stubbornness" (which is fine). But if that's not what you were asking about, please try your question again.

    Is there some way to change all matching length inputs from the same instance?

    You can't do this using global variables. You could pass in a scaling factor, but you would have to pass it in to each latestLine node - which would add quite a tangle of additional links. There are a few clever alternatives that could reduce the pain, however...

    It depends exactly what you are trying to do. If you just want to change the overall scale of your drawing, you can do that at the bottom by simply grouping your drawing and adding a scale node. So you make all your drawings at a standard scale and then, before publishing, adjust the final size using a scale node.

    I'm not sure what you mean by "matching" inputs. If you just wanted to adjust a subset of segments (like all the horizontal segments), this would be hard to do with a chain. But with the join end-to-end method where the segments are just one big list of independent paths, it would be fairly easy to add a test at the bottom to detect and filter out a certain subset of segments, apply some change to just those, put them back, and THEN do the join.

    If your adjustments are more complex and require something like a global variable passed to each latestLine node, one way to avoid the huge tangle of extra links passed into each node would be to still chain them together as you are doing now, but instead of passing just the previous line to each node, you could pass a list consisting of the previous line and the global-like variable.

    To do this, you would need to add a port to define this global variable at the top of your chain (maybe in your StartKnot node). Then, inside StartKnot and each latestLine node, instead of outputting a single line segment, you would use a combine node to output the segment AND the global variable.

    Then, on each latestLine node, you would change the previous line input port from value to list. Inside the subnetwork, you would take the "prev_line" null node receiving that input and branch off a "first" node and a "second" node. The first node would then hold the previous line segment; you would feed that into all the nodes below as before. Your second node would now hold the "global variable" passed in from above. You could then use that in whatever calculations you need it for.

    This is the trick I use in my iso_paper drawing system. It allows me to pass multiple pieces of information down through a chain of nodes with only needing a single connection between each link in the chain. If you change the "global variable" at the top, that change will ripple down through the entire chain. It's not a true global variable, but it's almost as good.

    Is there a way to show the grid as well as the knot without running it through the combine and copy at the end?

    Yes, by using the multiple value output technique I just described. This is another trick I do in my iso_paper drawing system. Each segment subnetwork in the chain passes along the grid as well as the previous segments. The grid is in one group and the previous segments are in a second group. This makes it easy to see both grid and knot as you render each segment. It also makes it easy to drop the grid at the bottom before you copy the segment threads to rotate them. One drawback is that passing along the entire grid each time eventually causes the drawing process to slow down a bit. If this becomes a problem, you could form subsets of your knot in separate chains, then drop the grids at the bottom of each chain before combining them for the final rotation.

    Why does the alt_grid give an error when I pass it through a colorize node?

    Because alt_grid outputs a list of points, and you can't color a point. A point is simply a pair of numeric values (x and y); there is nothing to color. To solve this problem, simply feed those alt_grid points into an ellipse node with height and width set to a small value like 8. This will turn each point into a "dot" that can then be colored however you want.

    Is there a more efficient way to achieve this setup?

    That's what I showed you in my previous note. If you are chaining together many copies of the same subnetwork, you will want to make that subnetwork as efficient as possible.

    Whenever my Nodebox programs start to bog down I immediately start hunting for inefficiencies. I render each node in my network until I find the node slowing things down and then look for more efficient ways of doing the same thing. I often switch from Viewer mode to Data mode. Sometimes, due to a bug, what looks like a simple line segment is really the same segment drawn over and over consisting of thousands of copies. So whenever I switch to data mode and scroll down to the bottom, if I see that there are 100,000 values when I was expecting only 100, I have usually found the problem.

    In this particular situation, there are really two different challenges: drawing the knot step by step, and rendering the final graphic. When drawing the knot is is quite helpful to see the grid at every step in the process, and this will make things a bit slower or messier. But once you have the final knot defined, you no longer need the grid.

    All you really need in the end are the values for each segment: angle and length. Once you have these, you could put them in a spreadsheet, read that into Nodebox using a CSV node, and then draw the knot directly from that data without needing a whole chain of subnetworks hooked together. You could draw the knot using just a few nodes and it would render very quickly. If that idea appeals to you, let me know and I'll show you how to do it.

    Whew! That was a lot of questions. Hope you are still there and still working on this!

    John

  5. 5 Posted by edgeofinnerspac... on 07 May, 2023 04:20 PM

    edgeofinnerspace's Avatar

    Oh yes, I'm still working on it. Just haven't had time to get back on here. So I think I was really just asking the same underlying question it seems. I can see it now, and I think I can sum it up for you: when dealing with me, specifically, if you feel like you might be repeating yourself, I am probably the one that's confused - meaning, I didn't see I was asking about the same thing in different ways. It appears I have the most trouble 'distilling' that underlying topic or problem in whatever I do. And anything revolving around math or coding exponentiates it because of my memory issues. In a situation where I need to voice a certain concept, I struggle to find words because I end up forgetting many of the basic points I want to make in the time that I am articulating any detals.

    I think, honestly, your isometric paper will be what I need to sit down and spend time with. The way you described that in your post is essentially the way I would visualize what it is I am searching for and was trying to find when I found nodebox. NodeBox is when I fnally realized I might be in the right neighborhood finally.

    I guess what I meant about adjusting from the point that is in this instance the one that is anchored is: being able to adjust an end point of one of the lines such that the two points that it is between are unaffected. Or I guess you could say, manipulating a line's 'start point' and keeping its end point fixed. so you ar adjusting a pont BETWEEN lines.

    I didn't realize that would be so hard to put into words. I think my issue is that I have no internal dialogue.

  6. 6 Posted by edgeofinnerspac... on 07 May, 2023 04:40 PM

    edgeofinnerspace's Avatar

    So what I have struggled with since starting the KryptoNauts project is this:
    how would I go about figuring out a system to define "traits" as in the concept used to generate large (10k+ piece) NFT collections?

    I am not sure if you are familiar with some of the more well-known NFT collections, but they are generative and several where 10,000 piece sets. But take, for example, Crypto Punks. There is the same underlying base layer which is the character's head. Then there are sets of traits/layers that you have a smart contract generate random combinations of. Traits like color, eyes (glasses, looking up+right, leftEyePatch, etc), mouth (pursedLips, grittingTeeth, etc), and so on. All these can be interchanged and then you have frequency of occurance of traits, etc.

    But for my collection, when I eventually release it as the 'trading card' type style that is gamified, I would like a release like that to be large. The concept I am describing to potential investors (so I can hire a developer!) is the first collection is coing to be smaller and more exclusive. These initial hand drawn "knots" are gointg to be what I call the "Primordial" knots. it will also help generate funding and hype as it will be a "pre-release" for early holders to gain access to exclusive features. And more rare simply because I'm designing each knot my self.

    The "Primordial" set then takes each of the knot designs which are carried over to a release I call the "Ancestral" knots, then a collection on cards called "Spectrum" or maybe "Continuum".

    What I have been racking my brain with is the traits and how I can discern any that would work as layers. If you spend any amount of time considering this problem the first thing you come to is, even if you can settle on a decent "base" set of nodes how do I figure out a system of switching out traits so that wherever lines intersect (technically, over or underlap, shadows will denote this in more polished versions - and this also adds to the complexity of this problem) that these lines remain 'flush' with themselves across the intersection?

    I don't know if I mentioned but one of the designs rules I have is that there are no turns where lines cross.and there is atleast that minimum space relative to the piece itself between parallel lines and also where lines passing over/under lines continue before they are allowed to turn....

    If that makes any sense, awesome. And this is why I say you are already my most valuable resource! As soon as I get any funding you get a tip big enough to have a designated mattress for hiding it in!!!! As long as I leave myself enough to do the same.

    Or maybe if you want to help, I let you be an independent advisor/consultant to the project. Remember, if you accept post office money orders, then its revenue, not income *wink wink*.

  7. Support Staff 7 Posted by john on 08 May, 2023 02:03 AM

    john's Avatar

    Edgeofinnerspace,

    Re adjustments to points BETWEEN line segments...

    I don't think your struggles with this necessarily have anything to do with head injuries. This stuff is subtle and I have to think about it very carefully to get to the bottom of it.

    There are two fundamental ways of thinking about your knots

    • a list of connected points
    • a list of joined line segments

    I made a quick demo to show the difference (attached). I show two knots made from the same starting points and with the same sets of angles and distances.

    • The red knot is a connected list of points
    • The blue knot is a joined list of line segments

    Try adjusting the start point and see what happens.

    • If you move the start point up and down (by changing it's Y value) you will see that none of the other three points in the red knot move, but the overall shape of the knot changes.
    • The same change will cause all three of the points in the blue knot to move up and down, but the overall shape of the knot remains fixed.

    A similar thing happens if you change the angle or distance of the first part of the knot.

    Both approaches are valid. Both can be used to define a knot. Both allow you to make individual adjustments, but those adjustments affect the overall knot in different ways.

    You said you wanted "to adjust an end point of one of the lines such that the two points that it is between are unaffected." In that case, you should use the red (connected points) approach. Changes to one segment will not move any of the inflection points, but will change the overall shape of the knot.

    My isometric paper and end-to-end join node uses the blue approach. I thought keeping the overall shape of the knot fixed during adjustments was more intuitive, but maybe I was wrong about that. Or maybe what is intuitive to me is not as intuitive to you.

    It all depends on how you tend to create and adjust your knots. If you want to use the red (points) approach, you can still borrow some of the other ideas from my isometric paper: expressing angles in multiples of 30s and distances in isometric units, chaining together points instead of combining them, and passing the grid from node to node in the chain so you can see that for reference while you are drawing.

    Hope this demo helps you think more clearly about your options. It will take some practice and experience to find the system that works best for you.

    (I'll respond to your second note separately.)

    John

  8. Support Staff 8 Posted by john on 08 May, 2023 04:10 AM

    john's Avatar

    Edgeofinnerspace,

    Re NFTs...

    Yes, I am familiar with NFTs and automated collections based on a system of traits. I have a few dozen NFT animations for sale on Foundation and have sold two of them to noted collectors. You can see my work and the work of three other Nodebox artists in this Cyber gallery:

    https://oncyber.io/nodebox_artists

    I prefer to create 1/1 pieces, each unique, but I know most of the action these days is with automated systems, either avatar trading cards, like Crypto Punks, or generative art algorithms like Tyler Hobbs' Fidenza.

    It's easy to employ random numbers at various inputs to an algorithm, but quite challenging to create a system where every random variation produces work that is noticeably different but still beautiful and still recognizable as the same "style".

    As a starting point you can add constraints to your system. You have already started this by restricting angles and distances to an isomorphic grid. Adding a "no cross" rule is another logical extension. This is definitely doable in Nodebox using my intersect_line node, but requires additional logic to test each potential new edge against all the edges that came before.

    Enforcing minimum distances between turning points and previous lines is also doable but tricky and will require some experimentation.

    Adding a weaving effect is also possible, but challenging. I have created woven pieces (where segments pass over and under each other, remaining "flush") but I've had trouble getting them to work consistently in a generic way.

    You can produce aesthetic knots by pouring random values into the top and culling any knots that fail your tests, but the number of possible combinations grows exponentially and you will soon run into long render times. Even then your results will probably still vary widely in overall quality,

    Producing consistently interesting and beautiful knots is a very hard problem. To really crack it you will probably need to think deeply about what drives your impulses when making knots. You are probably following some deep rules that your are not fully aware of.

    Nodebox is particularly good at helping you think through these problems and quickly try new effects. When it comes to minting knots on the blockchain, you (or your hired developer) will need to recode in some other language.

    As for me, I'm happy to help you grapple with interesting problems on this open forum. It's a great way for all of us to learn and deepen our craft. But I have no interest in hiring on as a consultant.

    I wish you luck on your journey!

    John

  9. 9 Posted by edgeofinnerspac... on 12 May, 2023 06:11 PM

    edgeofinnerspace's Avatar

    ok well, i DID have this typed out once. and then my browser inexplicably stopped responding - i disconnected from wifi, waited,...and waited.... and then some thinking it would catch up with itself. but ihave never experienced that before in all my time using any computer. so i will try again.
    --------------------------
    well, here is where is gets fun...

    by the way, if someone were to have me guess at which of those pieces were yours without ever having seen any of those before, i gotta say i nailed it. by the way, this is a really cool gallery. but even on my laptop that is

    dedicated for intense work (little to nothing installed and/or running on it) it is a bit laggy even on low quality settings. plus, im not that much of a fan of the AR stuff. nothing against you guys nodebox gallery. i thought for a

    minute i was on the nodebox EXCHANGE. and since i wasn't and also, since when i tried 'creating' ...well, anything on the site, i was funneled into having no choice but to use a premade world for any of the stuff i would build from

    there.

    i have to build from scratch or not at all. anyway. i would assume there is no NODE BOX EXCHANGE yet, which is why i've started building it. if people didnt find nodebox after this, well, i guess we're up the creek. so i will share

    this soon.

    this leads to my next point: the dapp/webpage for my kryptonauts will also be an NFT itself. so when you were to see it on a marketplace (other than the one built in to the dapp/webpage) the picture you see will be interactive as a

    dapp right there. (with the downside it can't call metamask, only walletconnect is possible that i can tell) the dap is an nft and the address for the contract is also the address where the dapp is located which is the page for

    minting the kryptonauts etc - of course, i will get an actual domain/url and host it too so it is basically a regular site.

    doing this for what i have started for the nodebox marketplace too!

    that said, i plan on using whatever is output from nodebox as SVG format and store it directly onchain too. it seems there s actually a way of having the contract also render this via canvas. i dont think there is a need for any

    other language except that of the smart contract language that is used.

    as for the traits. the idea is to actually have them randomly generated when someone mints one.

    so my example now will help clarify what i meant about the traits and where i would define them. i think you'll see what i meant a little better then. i was kind of sloppy when describing it the first time. with the attached pictures, for example, imagine we overlay a honeycomb pattern over them that would fit three 1 unit size rhombus(?)/diamond shaped inside each hexagon.., i think im describing it alright but if not that part shouldnt be too important but just that an area for each 'group' of traits that it always present could have however many subtraits that show up that could be different within each one. i think that was worded very odd but im tired as i sent too much time on sketch out a variant of the design last night.

    it looks rough but i think you see its the same general 'base' design but what changes with the subtraits is where those lines created by over/under passes happen. (so of course, this be dependant on the honeycomb pattern for them to be 'flush') but these subtraits would need to be 'flush' with each other - no line will appear from under another where it had not started from on the opposite side of the top line....

    gosh.. words... are not my friend today. idk. im just moreso frustrated i lost all of this i typed the first time too.

    what would you say is the best way of defining how these subtraits are going to be able to line up with the overall design at the edges of each 'honeycomb area' where they meet? i've been asking myself thisfor a year now. and i just dont know.

    i've thought one way would be instead of drawing the pattern like so, i only layout the FILLED area of the design (more like what i've currently been posting) that doesn't necessarily define if the line passes over or under itself. then the subtraits would be more of where i draw the shadows of one line on top of another and make sure no outlines are visible on the top section of line.... maybe this s part of the line vs point description you were talking about.

    anyway, the third attachment is a bunch of lines i was sketching on top of the design at one point just seeing what other variations of the pattern i would have just out at me for other ways this design would look in the end. but maybe it could give you some ideas too? i'm all over the place. i need some of mysignature CACAO COFFEE with oatmilk. (not because i'm trendy, just deathly allergic to whey protein.)

    finally, is there a list you have of where i find the actual links to the NFTs on the site you linked without actually viewing them on that one? for listing them on the NodeBox Market prototype!

  10. 10 Posted by edgeofinnerspac... on 12 May, 2023 06:17 PM

    edgeofinnerspace's Avatar

    this was an earlier design by the way, so it does violate some of the rules about no turns that are not visible or space between parallel sections of line to allow the space for a line to turn. there is an area in the encircled pattern at the edges where it looks a bit like a "W" where the ambiguity did work well here. however its not what im going for with KryptoNauts. i want what the line does to always be evident. but i felt this would be the quickest one to sketch a rough variation of for you last night.

    and not sure why those line breaks happened like that in the post above. i did type it in notepad the second time. because fool me once... well, i would be fooled if notepad would've frozen up on me i suppose ... highly unlikely.

  11. Support Staff 11 Posted by john on 12 May, 2023 10:17 PM

    john's Avatar

    Edgeofinnerspace,

    I agree that the cyber gallery is a little wonky to navigate through on a laptop. Cyber's UI still has some rough edges. Once we're all in the matrix this will be easier.

    You asked for a way to view the NFTs in the Nodebox Artists Exhibit directly without wrestling with Cyber's AR interface. One way is to click "View Assets List" in the upper right corner of the entry page.

    You'll have a cleaner user experience, though, by going to the source. There are four Nodebox artists in that exhibit, three on Foundation, one on Objkt (Tezoz blockchain):

    John Cartan: https://foundation.app/@jcartan

    Seohyo: https://foundation.app/@seohyo

    Freny Antony: https://foundation.app/@procedural_disarray

    Floris de Jonge: https://objkt.com/profile/florisdejonge/created

    As for weaving the strands of your knots over and under, I think I understand what you are trying to do. As I said, I have achieved this effect in several of my pieces. Here is one example:

    https://foundation.app/@jcartan/cartan1/1

    I did this using a weaving node I have not released because it does not yet work reliably. It takes a list of "thread" shapes and interweaves them automatically. But it would not work for your knots because it can't handle threads that intersect themselves. Still, I'm sure something similar could be made to automatically weave your knots. But it would not be easy.

    I agree with you that SVGs are the truest format to store Nodebox output. One idea I've long wanted to explore is interactive svgs, as described here:

    https://www.petercollingridge.co.uk/tutorials/svg/interactive/

    The basic idea is to wrap SVG text in a javascript/CSS wrapper that allows you implement simple forms of animation and interaction. In theory this approach could be used to create dynamic art pieces on the blockchain. Nodebox cannot do this by itself, but there might be a way to incorporate tag-like elements that could make it easier to create parameters, perhaps with some simple post-processing on the svg output.

    I'm not sure whether this technique would actually work and whether it would be practical for what you want to do, but it might be worth some research and experimentation.

    Hope this helps.

    John

Reply to this discussion

Internal reply

Formatting help / Preview (switch to plain text) No formatting (switch to Markdown)

Attaching KB article:

»

Already uploaded files

  • VOLT_(2).png 700 KB
  • emultStriker.png 145 KB
  • emultStriker.zip 17.9 KB

Attached Files

You can attach files up to 10MB

If you don't have an account yet, we need to confirm you're human and not a machine trying to post spam.

Keyboard shortcuts

Generic

? Show this help
ESC Blurs the current field

Comment Form

r Focus the comment reply box
^ + ↩ Submit the comment

You can use Command ⌘ instead of Control ^ on Mac

Recent Discussions

13 Jul, 2024 06:05 AM
11 Jul, 2024 03:48 PM
28 Jun, 2024 01:51 PM
27 Jun, 2024 02:56 PM
27 Jun, 2024 01:57 PM

 

26 Jun, 2024 08:17 PM
26 Jun, 2024 11:35 AM
24 Jun, 2024 02:42 AM
24 Jun, 2024 12:46 AM
23 Jun, 2024 08:07 AM
08 Jun, 2024 09:05 AM