onsdag, november 28, 2007

Præsentation

Det var så vores "8 minuts of fame"... og det gik da også nogenlunde!

Vores slides kan findes på http://www.daimi.au.dk/~abachn/oe/gamedev-uge48.pdf.

Vores extension hvor vores tidlige python model ligger, samt embedding af python ind i OE frameworked kan findes på http://www.daimi.au.dk/~abachn/oe/extensions/PythonModels/. Vores projekt der bruger denne extension kan findes på http://www.daimi.au.dk/~abachn/oe/projects/CreatePythonModels/.

onsdag, november 21, 2007

Udvidelser af Core OE: Resource Manager

Efter en snak med Ian og de andre OE gutterer vi begyndt at lave lidt om på ResourceManageren i selve OpenEngine, da den har nogle uhensigtmessige design valg.

Kort nævnt er det:

Der er kun et plugin pr file extension. Der er desværre ikke muligt at bruge et plugin på flere forskellige file extensions.

Pt har ResourceManageren kun en data path. Her kunne det være rart at have en form for PATH variabel som bestod af flere muligheder for søge stier.

[UPDATE] 28.11.07

We have updated both the IResourcePlugin class and the ResourceManager class to get the above results right.

The IResourcePlugin class/interface was extended with a list of the extensions this plugin knows how to handle. The idea is that when creating a new plugin you add the extensions that this plugin should handle. A plugin can be asked if it AcceptsExtension.

This is used in the ResourceManager to replace the map to just list. Given a file we just look through all plugins and ask if this plugin AcceptsExtension of the given file. So first task completed.

Next we needed to have a path system. We can AppendPath and PrependPath. The ResouceManager just keeps a list of these path elements. The important part is the function FindFileInPath that given a filename looks in the paths list and uses boost::filesystem::exists to determine if that filename exists somewhere. It returns the empty string if not found and the absolute/relative fullpath of the file.

tirsdag, november 20, 2007

Entydigt system bestående af punkter og afstande

Vi foretager mange designvalg, hele tiden, for at få et gennemskueligt og velfungerende system stablet på benene.

I den forbindelse er vi stødt på et problem med vores porte, som kræver at vi foretager et umiddelbart valg. Lad os først dokumentere problemet:

Et væsentligt langsigtet mål med vores system er at vores knogler/led/skeletobjekter er entydigt bestemt internt - Det på trods af at de kun består af afstande og punkter. Men, hele skelettet skulle også gerne være entydigt bestemt. Det skulle vores porte, i reglen, sørge for. Det har de også gjort hidtil, men det er nu gået op for os, at det ikke altid er tilfældet.

Sådan er det imidlertid ikke på nuværende tidspunkt. Helt basalt set er vores porte ikke orienteret korrekt. Vi låser, som det er nu, to objekter sammen ved at svejse deres porte sammen – det har den heldige effekt, at man kan orientere objektet man sætter på i 4 retninger, så man kan foretage en tilnærmelsesvis drejning i et led og ikke behøver skrue på de omkringliggende knogle-objekter meget.
Samtidig, og vigtigst, sikrer vi rigtig 3-dimensional placerings-afhængighed, idet portene nu er 1 og samme, og dermed har dens position indflydelse på partiklerne i begge objekter.

Problemet er, at objekterne ikke kan finde ud af hvilken side af den nye port netop deres partikler skal være på:



Det ene objekt, skoen, er opbygget af indbyrdes afstand, og er entydigt. Det andet objekt, læggen, er også opbygget af inbyrdes afstande og er entydigt.
Det at svejse portene sammen er ikke nok – der skal på én eller anden måde tilføjes endnu en constraint for at det holder. Vores opgave, rent programmeringsmæssigt, er at automatisere samlingen bedst muligt. Ideelt set skal brugeren af objekterne ikke kende til hverken skoens eller læggens opbygning; og han skal absolut ikke ind og beregne afstanden mellem to punkter i det nye objekt for selv manuelt at tilføje en constraint, det ville være ødelæggende for vores mix-and-match mål med bibliotektet.

Desværre betyder det her en generel udvidelse af vores arbejde:

1.
Vores porte ændres så de er 3dimentionale ved at tilføre én ny partikel, og kun en del af portene svejses, hvilket vil indbygge orientering i portene. Det betyder imidlertid at man, i designet af objekter, skal forbinde sig stramt til en væsentligt mere kompleks port: Hvis hele objektet er hæftet ved en 3dimensional port, kan man, i svejsningen, automatisk sætte en constraint på mellem de 2 partikler i portene som ikke er i plan sammen. De er nødt til, for at sikre at man kan rottere et led som nu, at være en slags små pyramidetoppe.

- Det er en puritansk løsning, som desværre gør hvert eneste led mere komplekst, og som gør at skrivningen af nye basisled, knogler, og større strukturer bliver mere kompleks. På plus-siden er den overkommelig: Der skal kun én ny fast constraint imellem den nye partikel i den ny porttype og vores hidtige knogler og led. Resten af konstruktionen ligger i den ny porttype. Det er smatidig heller ikke en uoverkommelig opgave at splejse de ny porttyper sammen, og vi kan, efter splejsnigen, glemme alt om porte og objekter og derfra kun arbejde med en liste af partikler og en liste af constraints.

2.
Vi løser problemet når vi sætter koordinater på: gennemsnittet af koodinaterne i det ene objekt skal ligge på den ene side af det plan porten udgør, gennemsnittet af koordinaterne for det andet objekt skal ligge på den anden side.

- Det er en rigtig snusket løsning som fritager os for ansvaret her ved at skubbe det fremad til instancieringen af koordinater. Vi skal bare sikre, som invariant, at vores objekter altid, i gennemsnitskoordinater, befinder sig på den ”rigtige” side af porten, og det gør ikke noget at nogen af partiklerne raver forkert. Det er lunkent, for hvis foden, i den tegnede analogi, bliver slået hårdt på runtime kommer den pludselig til at krænge op i læggen, og det er vi helt sikkert ikke interesserede i. Endelig kræver det, at vi, når vi producerer koordinater stadig bibevarer mulighed for at traversere legemet som objekter med porte.

3.
Vi gør det samme som ovenover, min vi udvidder openengine til også at forstå konceptet porte og skeletobjekter, og vi foretager hele beregningen på runtime. Så har vi oversat hele modellen til c++ og vi bruger kun python fordi det er ”et rart sprog”. Vi smadrer i øvrigt alt hvad der har med performance og gøre.

- kritiske kommentarer og grimme ord overlades til læserens fantasi.

4.
Vi udpeger en føle-partikel som har riggid-forbindelse til hver port i hvert objekt, og giver variabler med for porten og føle-partiklen frem til koordinatisering/runtime. Når porte svejses arves følepartikler fra de to forældre-porte. Vi foretager lejlighedsvis, men først i forbindelse med koordinatisering/runtime, en point-plane-comparison til begge følepunkter tilkoblet en svejset port. Er de på samme side smides det ene følepunkt over på den anden side.

- Hvis ikke denne løsning fremføres helt op til runtime har den samme svaghed med inadkrængende objekter som løsningen ovenover, men den vil være relativt billig at checke på runtime i forhold til.

5. Alle punkter i alle objekter holder sig på deres side af portene. Det giver problemer i forhold til punkt 4, se illustrationen nedenunder, hvor en stor rigidbody har en port med partikler på begge sider. Her skal objekterne bibevares helt frem til det tidspunkt hvor checket køres.


Som det kan ses accepteres en del af partikler ikke (de gule).


- Ærgelig løsning, som kræver bibevarelse af mange variable for at adressere objekterne individuelt langt hen i processen.

6. Ligesom i punkt 4 anvendes følepartikler, men denne gang defineres på slum for hver følepartikel en constraint, hvori portstørrelsen indgår som faktor. Det gælder så generelt, at partiklen som minimum er ½ portstørrelse væk fra porten, og at dens constraint til enhver anden følepartikel maximum rager ½ portstørrelse ind over dennes. Afstandene er angivet i afstande vinkelret på planet porten udgør. Derudover må det gælde, at alle portens 4 partikler have kortere afstand til følepartiklen, end dens minimumsafstand til den anden følepartikel. Når portene splejses sørger partiklerne for automatisk at oprette disse minimums-constraints.

- Svær at dokumentere forståeligt, og designet af basisled problematiseres noget. Følepartiklen skal vælges til at være centralt placeret i forhold til sin tilhørende port, men så længe den befinder sig ”oven over” porten så går det. Hvis ikke constraintsne overholdes nøje risikerer man inkompatible led/knogler.

_______________

Gruppen hælder for øjeblikket mod model 1, og vi ønsker at beslutte os for en løsning inden fredag, men det er forhåbentligt den sidste større problemstilling i vores modelleringsarbejde =]

Skelletbibliotek og krav til led, knogler med videre

En af de problemstillinger vi løbende har forhold os til er at objekter som består af afstande og punkter kan opfylde afstandskravet i en række forskellige orienteringer. Det indgår i designet af hvert eneste af vores led og hver eneste af vores knogler, som endeligt successkriterium, at afstandskravene opfyldes hvis og kun hvis ledene har præcist den form vi ønsker.

Der kan opstå problemer med tvetydigheder i forhold til dette mål - lad os forholde os til vores generelle drejeled som eksempel.
Hvis vores generelle drejeled een gang har taget en omgang for meget forbliver det i den drejede tilstand og er stadig funktionsdygtigt - på samme måde som metallåget på mange flasker kan drejes for tæt til og så "hopper" gevindet en omgang op og bliver løsere igen. 

Men vores led kan i nogen situationer, i modsætning til metallåget, være i stykker: hvis en 3d model af en underarm er bundet fast til partiklernes koordinater, er modellen nu blevet snoet en gang, og fysikmodellen siger stadig, at armen er lige så funktionsdygtig som før.

Det er imidlertid kun et problem som opstår, hvis en partikel udsættes for så stor kraft at ledet går i stykker i første omgang, i løbet af een af fysikmotorens verlet-integration iterationer. Her har vi valgt at stå af, i første omgang, for et naturligt svar vil være at lave en model som har et mindre perfidt led så constrainten bliver sværere at overtræde. Det gælder her generelt, at der skal enormt meget mere kraft til at overrumple et drejeled med 180 graders drejespan, end et led med 359 graders drejespan. Alternative svar er at sætte antallet af fysik-iterationer per sekund op, at bygge og anvende en version af drejeledet med hjælpepartikler, eller at lave et runtime tjek på at partiklerne i drejeledet ikke bliver udsat for en for stor udefrakommende resulterende kraft. Med andre ord må det, pt, være brugeren af vores systems ansvar at sikre, at han ikke ødelægger det ved at begå vold mod et led som han selv har bestemt skal være svagt.

Til gengæld kan vi garantere mere for de mere specifikke led vi laver - vores eget underarms-drejeled, for eksempel, er designet med et span på netop omkring de 180 grader.

Men vores system er altså ikke fejlfrit, hvis ikke det bliver anvendt med omtanke, og det siger vi faktisk god for. Det er et generelt bibliotek til at modellere skeletter og led med, og skulle man ønske at implementere led der kan vrides i stykker i 3d med nøje specificerede krafter må man selv udbygge biblioteket med markeringer af partikler der indgår i svage led eller lignende.
Ligeledes gælder det samme hvis man ønsker for alt i verden at undgå overvridning, fordi man har en særlig voldsom fysikmotor.

Og skulle det vise sig at det generelle bibliotek har problemer med at fungere tilfredsstillende i openengine må vi blot lave en openengine udvidelse :-)

mandag, november 19, 2007

Testing python, ruby and lua bindings...

Vi har oprettet en extension og et projekt der tilsammen tester de 3 forskellige bindings klasser. Der er her gjort mest ud af Python bindings testene da det er dem som vi selv skal arbejde videre med.

Vores test extension kan findes på:

http://www.daimi.au.dk/~abachn/oe/extensions/BindingsTest/

Denne extension bruger PythonBindings, RubyBindings, LuaBindings og ScriptBindings. Kig her på bloggen omkring hvordan du får fat i dem.

Vores test project kan findes på:

http://www.daimi.au.dk/~abachn/oe/projects/EmbedBindingsTest/

Disse tests er ikke vores endelig projekt, men er mere proof of concept på at det vi har gang i kan lade sig gøre. Derfor vil disse ogsåvære fyldt med forskellige eksperimenter som kan være mere eller mindre brugbare!

Embedding python in C++

Så er det lykkedes at definere en C++ klasse, exportere den til Python. Oprette en liste af objecter af denne klasse i python og kalde en exportet function fra C++ hvor denne liste gives med. Denne function i C++ modtager nu listen og gennemløber denne for at udskrive elementer i denne.

C++ klassen:

class Point3D {
public:
double x, y, z;
Point3D(double cx, double cy, double cz) : x(cx), y(cy), z(cz) {};
};


C++ callback functionen

void printListPoint(object const& ob) {
stl_input_iterator begin(ob), end;
std::list il(begin, end);
for (std::list::iterator itr = il.begin(); itr != il.end() ; itr++) {
std::cout << (*itr).x << std::endl;
}
}


Export af functionen fra C++ til Python

BOOST_PYTHON_MODULE(hello)
{
def("printPointList", &printListPoint);

class_("Point3D", init())
.def_readonly("x", &OpenEngine::Scripting::PythonTest::Point3D::x)
.def_readonly("y", &OpenEngine::Scripting::PythonTest::Point3D::y)
.def_readonly("z", &OpenEngine::Scripting::PythonTest::Point3D::z)
;
}


Python coden der bliver kaldt:

import hello

p1 = hello.Point3D(1.1, 2.2, 3.3)
p2 = hello.Point3D(2.1, 6.2, 7.3)
p3 = hello.Point3D(3.1, 7.2, 8.3)
p4 = hello.Point3D(4.1, 8.2, 9.3)

pl = [p1, p2, p3, p4]

hello.printPointList(pl)


Output fra dette script!!

1.1
2.1
3.1
4.1


Som det kan ses så har vi oprettet nogle objecter i python, som vi så har sendt tilbage til C++, så vi der kan arbede videre med dem!

Næste skridt... i C++ lave instancer af nogle nogle python definerede klasser!!

Extension: LuaBindings

Extension name:

LuaBindings

Location:

http://www.daimi.au.dk/~abachn/oe/extensions/LuaBindings/

Purpose:

Create a abstract base class for integrating Lua into OpenEngine. This class should be used as a super class for your more specific extension that wants to execute lua scripts.

Dependencies:


Implementation details:

We have used the standard lua C API to implement the lua integration in OpenEngine. This abstract class gives the ability to run scripts or run entire lua files. Before each run a Pre() method is called and a Post() method os called after the script has run. These can be overwritten in a subclass, but are here given the default behavior of nothing. A default environment is setup before each run. Subclasses have to specify a Init() method when subclassing from this class. This Init method is used to export functions from C++ to lua.

Extension: RubyBindings

Extension name:

RubyBindings

Location:

http://www.daimi.au.dk/~abachn/oe/extensions/RubyBindings/

Purpose:

Create a abstract base class for integrating Ruby into OpenEngine. This class should be used as a super class for your more specific extension that wants to execute ruby scripts.

Dependencies:


Implementation details:

We have used standard ruby C API to implement the ruby integration in OpenEngine. This abstract class gives the ability to run scripts og run entire ruby files. Before each run a Pre() method is called and a Post() method os called after the script has run. These can be overwritten in a subclass, but are here given the default behavior of nothing. A default environment is setup before each run. Subclasses have to specify a Init() method when subclassing from this class. This Init method is used to export classes and methods from C++ to ruby.

onsdag, november 14, 2007

Extension: ScriptBindings

Extension name:

ScriptBindings

Location:

http://www.daimi.au.dk/~abachn/oe/extensions/ScriptBindings/

Purpose:

Common super class to all scripting languages we want to embed into OpenEngine.

Dependencies:

  • None


Implementation details:

This is a simple abstract class that defined some virtual methods which can be overridden in subclasses to give a more meaningfull behavior.

Toptunet drejeled

Vores drejeled har nu nået 4. iteration. Men før vi kaster os ud i beskrivelsen af den vil vi lige kort nævne iteration nummer 2 og 3:

Som det kan ses var anden iteration en stor konstruktion.

Det har sine årsager, men lad os starte med at sige, at vi redegør for de første led, ikke fordi de er gode, men fordi de illustrerer hvor store fejl man kan begå når man forsøger at modellere geometrisk funktionalitet i software.

2. Iteration:
Ideen er taget fra vores kugleled, hvor der sidder constraints fra alle partikler til alle partikler, og hvor minimums-afstandene mellem de to pyramidebunde kan forøges til det tidspunkt hvor de passer med, at ledet er helt strakt ud hvis det ikke er twistet - men det kan i den konstruktion give sig en del hvis man twister partiklerne i bunden af den ene pyramide 45 grader omkring midteraksen på figuren, hvorfor modellen er mangelfuld. Ydermere kan man ikke sætte grænser for rotationsgraden, så den dur ikke rigtig; Iteration 2 baserer sig på at forøge antallet af partikler som har minimumsafstande, altså i stedet for to pyramider hvor partiklerne i bundene ikke må komme for tæt på hinanden er her to figurer som er en approximation over flade kegler. På tegningen er et antal af gule minimumsafstande angivet. Men kegler passer ikke ind i vores system med porte, så derfor er der spændt porte ovenpå og nedenunder konstruktionen, og midterpartikler er nødvendige adskillige steder for at afstive strukturen.

Alt i alt er dette led håbløst indviklet, og ignorerer geometriske regler til fordel for et viderearbejde med noget, som er tried and true.

3. Iteration :

Her har vi genvundet fatningen lidt:
Dette led består af 4 pyramider, og portene er markeret med blåt. Det bærende princip er, at vi ønsker at kunne rottere 2 figurer som er placeret oven i hinanden i forhold til hinanden:
Det at fysiske led ikke kan have overlappende dele, betyder ikke, at vi behøver arbejde med den begrænsning. Vi kan tvært imod udnytte, at vi har mere fleksibilitet til rådighed. Vi kiggede derfor lidt på det, og indså, at vi kunne placere partikler på en cirkel ved at angive afstande til to punkter. Herfra var ideen at konstruere to centralt placerede overlappende firkanter, der altså havde partikler som kun bevægede sig på cirkelbuen, og så lave constraints på dem. Det er de to kongruente figurer, en sort og en grøn, som hver har 8 kanter.
De bliver hver låst fast på en port ved hjælp af lidt constraints.

4. Iteration

Men det viste sig, at det kan optimeres yderligere:


Her har vi udnyttelse af summen af ting fra de andre led: vi spender to porte direkte på 2 partikler med faste constraints. Det giver 2 dobbelt-pyramide konstruktioner, som bedst beskrives ved, at hver port laver to pyramider, som hver møder en af den anden ports to pyramider i spidsen. De er fint defineret i forhold til hinanden, og er ubevægelige i forhold til de to faste constraints, så såfrem man gør sit arbejde ordenligt er der ikke problemer. Den grønne constraint er tegnet på for at illustrere, at justerer man på max-størrelsen af den, så kan man justere drejbarheden af den ene pyramide i forhold til den anden.

5. Iteration

Men kan det gøres endnu bedre? her må svaret være ja - det kan det. "Man behøver kun at definere 3 afstande fra 3 punkter på en rigid-body til "noget andet" for at forholdet er bestemt": Det er en regel vi nu har fået praktisk erfaring for at bruge. Så det gælder altså for hver af de 4 dobbeltpyramider, at der kan undværes en constraint op til spidsen. Men vores fysikmodel anvender verletintegration, hvilket gør at man ikke kan stole helt så meget på, at afstanden mellem partiklen og pyramidetoppene er bibeholdt i korrekt det sted hvor constrainten (som ideelt set allerede er opfyldt) er sat på. 
Men man kan imidlertid foretage flere verletintegrationer hvis man kun arbejder med 25 constraints, end hvis man arbejder med 29. 
Og precisionen øges også med antallet af iterationer - så her er der tale om en afvejning.
Under alle omstændigheder er der kun tale om en lille optimering, så den vil vi ikke dokumentere yderligere.

tirsdag, november 13, 2007

Vores led

Lad os tage fat på beskrivelsen af de første led:

Tidligere har vi beskrevet et drejeled, fordi det umiddelbar var det mest komplekse led vi stod overfor. Hvorvidt vi får det implementeret i koden vil tiden vise, for det er ikke nær så essentielt som de andre led: Vi har studeret menneskelige led og knogler i materiale vi har skaffet, og det viser sig at drejeledet primært er nødvendigt for at modellere menneskers underarm. De andre ledtyper - hængselled og kugleled - er derimod anvendt overalt i kroppen.

Så derfor vil vi her fokusere på det design vi har lavet af kugleled og hængselled

Det kugleled vi har planlagt ser ca. således ud:



Dette led består af to kongruente pyramider, som er sat sammen ved spidsen. De to pyramider kan rottere frit i forhold til hinanden i vores mest basale model, så længe de ikke rotterer ind over hinanden. De er lavet ved hjælp af faste afstande partiklerne imellem, hvorfor der ikke er behov for diagonal-constraints i bunden. Det er illustreret på tegningen med de røde streger, der er constraints med en minimumsafstand som er ca. det samme som afstanden mellem to partikler i en af pyramidernes bund. Men her slutter det ikke - udover de tegnede constraints er det faktisk nødvendigt med samme minimumsconstraints fra alle partikler i den ene pyramidebund til alle partikler i den anden pyramidebund. Det er fordi pyramiderne selvfølgelig også kan "twistes" i forhold til hinanden. Vi vil forsøge at tilføje en tegning hvor alle constraints er sat på senere.

Hvis man ønsker at begrænse ledets twist-evne kan det forsøgsvis gøres ved at lave maksafstande på de røde constraints - men de skal beregnes nøje, og vi har endnu ikke undersøgt præcist hvordan det vil ha indflydelse på ledets bøjeegenskaber, og det bliver højest sandsynligt noget som bliver sat på når vi har mulighed for at visualisere det på skærmen.

Det næste led vi har arbejdet med er et universelt hængselled. Universelt, fordi vi ønsker at kunne begrænse hvilke vinkler det kan bøje sig indenfor.

Det ser således ud:

Det består af to prismer med lige stor højde og ligedannede trakenter som grund-areal.
Det er væsentligt at bemærke, at der på alle firkantede overflader i figuren er der behov for diagonaler.
Trekanterne i "bunden" (på tegningen ses de fra siden) skal forestille at være trekanter hvor alle vinkler er 60 grader. Endvidere gælder det for alle constraints som ikke er diagonaler i prismerne, at de har samme længde, og at denne længde vil blive givet med til ledet i dens constructor.
Den røde trekantsfigur som er tegnet på markerer en rød constraint og en rød vinkel. Det er fordi vi er i stand til at beregne længden af den røde constraint, der er en min/max constraint, som begrænser hvor meget leddet kan bevæge sig. Som standard vil man sige, at trekanterne ikke må gå ind over hinanden.
Vi kan, ved hjælp af sinusrelationen, den røde vinkel, og de røde kateter som støder op imod vinklen beregne hvor stor constrainten skal være for at låse leddet i en given vinkel. Envidere kan vi  anvende samme relation til at angive minimumslængde og maksimumslængde for constrainten, for på den måde at begrænse ledets bevægelsesevne. Det gør at vi kan modellere et knæled, der jo ikke kan bøjes fremad, for eksempel. At gøre det samme for den sorte vinkel og den sorte constraint gør blot at vi kan præcisere det yderligere.

Vi har også designet et udviddet drejeled, som vi vil snakke om senere, når vi har fået tegnet og dokumenteret det lidt bedre.

Design af skeletsystem, porte

Vi er nu nået til at arbejde med en konkret pythonimplementering af vores led, men først vil vi gerne snakke lidt om hvordan vores design flasker sig.

I den forbindelse har vi lavet en masse designarbejde, hvoraf jeg vil forsøge at gøre rede for noget af det her.

I pyhton er vores vigtigste mål, at producere et bibliotek med led og skeletdele, der kan sættes sammen på kryds og tværs af hinanden. Det gør vi objektorientere. Det vil sige, at hver skeletdel består af skeletdele eller er defineret ved hjælp af et basis.

Det eneste openengine er i stand til at forstå, er i øjeblikket partikler og constraints, så vores pythonobjekter skal nødvendigvis bestå af disse dele for at openengine kan forholde sig til dem. Med andre ord er vores basis: partikler og constraints.

For at producere et bibliotek med led og skeletdele må vi starte et sted, og da vi på sigt er interesseret i at vores bibliotek skal anvendes til ragdollfunktionalitet er det med ledene vi starter.
Men for overhovedet at producere led må vi være klar over hvordan vi har tænkt os, de forskellige skeletdele skal sættes sammen.

Vi har valgt at anvende en port-abstraktion. En port er i vores model 4 partikler der har constraints til hinanden. Hvis man er bekendt med geometrisk triangulering ved man, at et punkt defineret ved een afstand til et fast punkt kan ligge hvor som helst på en kugleskal, et punkt defineret ved afstande til 2 punkter gør at punktet kan ligge hvorsomhelst på en cirkelkant, hvorimod et punkt defineret ved afstande til 3 punkter nødvendigvis må ligge på eet bestemt sted.

For at integrere to systemer fast i forhold til hinanden i vores system, der kun har partikler og afstande, må de to systemer nødvendigvis være fælles om 4 punkter, der er defineret med afstande i forhold til hinaden. Fordi vi ønsker at vores led skal vende rigtigt i forhold til hinanden og kun klistrer sammen på bestemte steder er porte den bedste abstraktion vi har adgang til. Porte har, derudover, en universel form, således at vi kan optimere ved at kombinere to porte der er sat sammmen til 4 punkter uden at skulle forholde os til form, men kan nøjes med at kigge på størrelse. Vores porte ser ca. sådan her ud:


Så det gælder altså, at alle vores led og senere også vores knogler kommer til at anvende porte.

Vi har ikke besluttet om vores porte også skal have een universel størrelse endnu, men det kan godt være det viser sig at være lettest. Vi har endnu ikke forholdt os præcist til, hvordan vi ønsker at kunne skallere vores skeletter og lignende, men det gælder utvetrydigt, at hvis alle afstande i alle contraints bliver ganget med samme konstant vil systemet skalere, så det er kun relevant hvis vi ønsker forskelle i portstørrelse inden for samme figur. Indtil videre går vi ikke ud fra at vi har en universel størrelse, kun en universel form.

lørdag, november 10, 2007

løsning på drejeled

Et drejeled is er et meget begrænset led, som er i stand til ar dreje de opmodliggende knogler i forhold til hinanden. Vi arbejder for øjeblikket med en fysikmodel, der kun tilader partikler og constraints som afgrænser afstandene mellem partikler. Ved hjælp af modellen er vi kommet på 2 løsninger:

- A freespinning 1 point-joint with minimum-distance restrictions between points on either end of the joining point.

a 40 degrees box-skewing 4 vs. 4 points

Første mulighed giver leddet en evne til at rottere rundt og rundt på samme måde som et bilhjul, men de to ender af leddet er ikke nødvendigvis parallelle, så det har karakter af at være et kugleled. Det kan afhjælpes gevaldigt ved at tilføje flere partikler i den ene side af leddet, men vi ønsker at vi kan bygge skeletter ved hjælp af et universelt forbindelsesled, bestående af 4 partikler, så der skal sættes en yderligere forbindelsesstruktur ind.

Anden mulighed er den vi aktivt har arbejdet med:

Her er ideen, på den enkelte figur, at de hele streger er på forsiden og de stiplede er på bagsiden. De brune streger har en minimumslængde som er ca. 60% sammentrukket, og de er på billedet udstrukket i deres maksimumslængde. De røde siplede og de grønne hele udgør samme constraint: De har på billedet deres minimumslængde, og ingen maksimumlængde. Endelig har de blå stivere en konstant længde, og det har de sorte firkanter i hver ende også. Figuren hvor firkanterne er sat oven på hinanden er der, for at illustrere hvordan man kan opnå mere drejbarhed end ca. 40 grader.
Det enkelte leds funktion er, at i takt med at de brune bliver kortere, så vil figuren blive kortere, men på grund af de blå stivere bliver den nødt til at dreje, så den øverste ende drejer med uret. De grønne stivere er primært med for at sikre, at toppen ikke kan dreje imod uret.

Det er lidt svært at forklare hvordan det virker med ord, så hvis man har mulighed for at sætte sig med en terning eller lignende, og tegne de enkelte constraints, så vil det måske lette lidt på forståelsen.

Vi har ikke implementeret nogen af ideerne endnu, men i sidste ende vil det komme an på hvilken type drejeled man ønsker, og hvilke resurser man har til rådighed i forbindelse med beregninger.

tirsdag, november 06, 2007

Extension: PythonBindings

Extension name:

PythonBindings

Location:

http://www.daimi.au.dk/~abachn/oe/extensions/PythonBindings/

Purpose:

Create a abstract base class for integrating Python into OpenEngine. This class should be used as a super class for your more specific extension that wants to execute python scripts.

Dependencies:


Implementation details:

We have used Boost Python to implement the python integration in OpenEngine. This abstract class gives the ability to run scripts og run entire python files. Before each run a Pre() method is called and a Post() method os called after the script has run. These can be overwritten in a subclass, but are here given the default behavior of nothing. A default environment is setup before each run. Subclasses have to specify a Init() method when subclassing from this class. This Init method is used to export classes and methods from C++ to python.

mandag, november 05, 2007

Så er der plan!



Her har vi så vores relativt løse plan. Den er ikke helt korrekt afstemt, og har mest form af at være et kladdepapir, men redegør alligevel for størstedelen af hvad vi fik diskuteret ved første møde. Det må forventes at vi næste gang revurderer planen, skriver den op igen, og får nedfotograferet en lidt pænere udgave.

Python integration i C++ og CMake

Målet for dagens arbejde var at lave en simpel klasse der havde python embedded så det var muligt at eksekvere externe python script. Derudover skulle CMake udvides så den fandt både boost_python og python.[h|dll] på ens platform.

Det at lave en embedded python klasse vha boost_python var let. Klassen er tænkt som en superklasse til andre mere specifikke anvendelser af denne funktionalitet. På nuværende tidspunkt har den en konstruktør og en run metode. Konstruktøren tager en base sti til alle de script man vil loade og run metoden tager det script navn som skal køres. Dette virker uden problemer.

Denne extension kan findes på http://www.daimi.au.dk/~abachn/oe/PythonBindings/

Vi har også lavet et simpelt projekt som tester at vores PythonBindings klasse virker, compiler og linker korrekt.

Dette projekt kan findes på http://www.daimi.au.dk/~abachn/oe/PythonEmbedTestsProject/

En meget større udfordring var det at få CMake til at finde de rigtige python libs og include paths. Dertil skulle der også udvides i den allerede eksisterende boost del af CMake opsætningen da vi også skulle bruge boost python abstraktion.
Der vil komme mere til dette når vi har fået afklaret hvordan dette skal distribueres.