PDA

View Full Version : Does anyone have advice on sorting?


Scott Ayers
08-26-2010, 03:44 PM
Coffee doesn't seem to have a sort function as far as I can tell.
So I'd like to learn how to create sorts from scratch. But I'm having difficulty figuring out how to approach this.

What's the best way to do this?
Should I create a custom array and then fill it with the object names. Then try to sort that array?
There are no built in functions that count objects in the OM like the GetPointCount() function does. So how would I go about counting the objects I want to sort so I can use that to tell the loop when to stop?

Does anyone have any advice on how to approach the sorting and arranging objects by their names?

-ScottA

imogwaii
08-27-2010, 09:33 AM
I have no clue about coffee..so perhaps this post is totally unusefull, but why not use Python? It has really good sorting algorithms implemented.
Look here: http://wiki.python.org/moin/HowTo/Sorting/
Its not totally intuitive, but with a bit of trying i got great results from it. :)
cheers
alfred

Scott Ayers
08-27-2010, 04:04 PM
Thanks for the link.

I know Python has a built in sort function. So does Java, C++, .NET, etc... and people always say to use them rather than building your own sort. But what if you're working in a language like Coffee that doesn't have a sort function?
This kind of thing is why I prefer to learn how things work in case I need to built it myself. Rather than depending on someone else providing (or in this case not providing) something for me.

I can do some very crude sorting with Coffee like this: while(op)
{
var first = doc->GetFirstObject();
var next = first->GetNext();

if(first->GetName() > first->GetNext()->GetName())
{
first->Remove();
first->InsertUnder(next);
}
else break;
op=first;
EventAdd();
}

But this has a lot of limitations and needs to be enhanced.
It uses the top of the hierarchy to bounce off of and sort the objects. So it sorts everything instead of only selected objects.
And the object's names have to already be in sequential order for it to work.

I was hoping someone out there might have a better way to do this kind of thing.
Possibly by maybe doing it like this?:
-Copying the selected objects to sort
-Pasting them into a temp document
-Do the sorting
-Then paste it back to the original document and kill the temp doc

I'm just spit balling there. And that might not be the best approach.
So I would like to know if anyone out there has done any sorting with Coffee. And can offer any ideas.

-ScottA

unseenthings
08-27-2010, 08:20 PM
Hey Scott,
Yeah, back in the day you had to write your own sort routines... a bubble sort is one that I used a lot, but there are better options these days. While not in coffee, you may want to take a look at the Insertion Sort (http://en.wikipedia.org/wiki/Insertion_sort) page on wikipedia -- it has some very simple pseudo-code that should translate very easy to coffee based on what you've already got.

I haven't done any coffee scripting in quite a while, so I can't help you on the selection side, but hopefully this will move you closer to where you're trying to get.

Scott Ayers
08-27-2010, 10:30 PM
Thanks for the link.
But I'm not sure if I know enough yet to use that kind of information.
I keep running into problems with simple loop logic. Much less trying to convert a completely different language into a Coffee equivalent.

Here's another example: var startobj = doc->GetActiveObject();
var startname = startobj->GetName();
var nextobj = startobj->GetNext();
var nextname = nextobj->GetName();

while(startobj)
{
if(startname > nextname)
{
startobj->SetBit(BIT_ACTIVE);
println("true");
startobj->Remove();
startobj->InsertAfter(nextobj);
}

if(startname < nextname || op->GetNext() == null)
{
op->DelBit(BIT_ACTIVE);
}
else break;
startobj = startobj->GetNext();
}

This will make the selected object travel down the hierarchy until it's name no longer is greater than the next object's name. Resulting in a sorted hierarchy.
But it has problems.
I have to keep hitting the execute button manually and I can't get it to move the object down the last position automatically. And then I can't figure out how to let go of that object that was just sorted and select the first object in the list and start the process over again.

I keep get stuck on the approach of how to write this code.
I know all of the code pieces needed to do this. I just can't figure out how to construct them together properly. :sad:


-ScottA

rui_mac
08-27-2010, 11:46 PM
Do you just want to have a whole scene sorted based on the names of the objects? Of course, this sorting would only occur on the "first level" objects, not on the child objects.

Rui Batista

Scott Ayers
08-28-2010, 12:56 AM
I'm interested in any type of sorting that you, or anyone knows how to do. And is willing to share rui.

I guess the ultimate sort solution for me would be to sort only the selected objects in the hierarchy. But it really doesn't matter.
I'm just looking for examples that I can use to learn from.

-ScottA

rui_mac
08-28-2010, 01:12 AM
This script will sort all objects of your scene, according to their names.
It keeps all child objects intact, only sorting the "first level" objects.
It is a very simple "Bubble Sort".
I added an Undo so that you can return your scene to the original state, if wanted :-)
See if this helps.

Rui Batista

Scott Ayers
08-28-2010, 01:55 AM
Thanks rui. That's good.
It's nice to have a working example with the strcmp function in it.

What about a script that will then take those sorted results and put them into a Parent->Child hierarchy? Like a chain of joints for example.
That was the other type of thing I was trying to do.

-ScottA

rui_mac
08-28-2010, 09:21 AM
Can you explain a little better what you mean by that? it should not be hard to do but I need to know exactly what you want :)

Rui Batista

Scott Ayers
08-28-2010, 02:19 PM
Never mind Rui.
I eventually figured it out. And I've managed to create some pretty cool sorting scripts with your help.

Here's a script that will only sort the objects that are selected in the OM: // Sorts only selected objects

var changed;

sort(doc,op)
{
var next_op;
while(op)
{
next_op=op->GetNext();
if(next_op)
{
if(strcmp(op->GetName(),next_op->GetName())>0)
{
doc->AddUndo(UNDO_OBJECT,op);
op->Remove();
op->InsertAfter(next_op);
changed=True;
}
}
op=next_op;
}
}
main(doc,op)
{
changed=True;
CallCommand(100004772); // Group Objects
while(changed)
{
changed=False;
sort(doc,doc->FindObject("Null Object")->GetDown());// Start loop from the first child of the Null
}
CallCommand(100004773); // Expand Object Group
var selected = doc->GetActiveObject();//The Null is still active at this point
selected->Remove();// Delete it from the scene
CallCommand(100004767); // Deselect all--->just to be safe
}

And here is a script that will sort and arrange just the objects that are selected in the OM into a parent->Child hierarchy: //This script will convert only the selected objects to a parent->Child hierarchy
//The forwardSort method doesn't do anything. But I left it there if needed by the user

var changed;

reverseSort(doc,op)
{
var next_op;
while(op)
{
next_op=op->GetNext();
if(next_op)
{
if(strcmp(op->GetName(),next_op->GetName())<0)
{
doc->AddUndo(UNDO_OBJECT,op);
op->Remove();
op->InsertAfter(next_op);
changed=True;
}
}
op=next_op;
}
}

forwardSort(doc,op)
{
var next_op;
while(op)
{
next_op=op->GetNext();
if(next_op)
{
if(strcmp(op->GetName(),next_op->GetName())>0)
{
doc->AddUndo(UNDO_OBJECT,op);
op->Remove();
op->InsertAfter(next_op);
changed=True;
}
}
op=next_op;
}
}

childSort(doc,op)
{
var next_op;
while(op)
{
next_op=op->GetNext();
if(next_op)
{
if(strcmp(op->GetName(),next_op->GetName())>0)
{
doc->AddUndo(UNDO_OBJECT,op);
op->Remove();
op->InsertUnder(next_op);
changed=True;
}
}
op=next_op;
}
}


main(doc,op)
{
changed=True;
CallCommand(100004772); // Group Objects into a temp Null
while(changed)
{
changed=False;
reverseSort(doc,doc->FindObject("Null Object")->GetDown());
}
CallCommand(100004773); // Expand Object Group
var temp = doc->FindObject("Null Object");
temp->GetNext();
temp->DelBit(BIT_ACTIVE);
childSort(doc,doc->FindObject("Null Object")->GetNext());
temp->Remove();// Remove the temp null object
}

Thanks for your help Rui.
I never would gotten this far without your help.

-ScottA

CGTalk Moderation
08-28-2010, 02:19 PM
This thread has been automatically closed as it remained inactive for 12 months. If you wish to continue the discussion, please create a new thread in the appropriate forum.