Well this one's a little more tricky!
This time instead of rotating the polygons, the texture is effectively rotating instead. So I can't see a way of doing it without transforming the points. Although it is much simpler than my last attempt
Rem Project: ShadowPlaneOnAnObject
Rem Created: 28/10/2005 16:33:27
rem Technique: A casting object provides the XYZ coordinates to place
rem a shadow using UV data manipulation of a transparent shadow mesh.
rem Make shadow texture
cls rgb(0,0,0) : box 1,1,15,15
get image 1,0,0,16,16
rem Make the object
make object box 1,5,1,5
make mesh from object 1,1
add limb 1,1,1 : offset limb 1,1,3,0.25,4
add limb 1,2,1 : offset limb 1,2,-3,0.25,4
add limb 1,3,1 : offset limb 1,3,-3,0.25,-4
add limb 1,4,1 : offset limb 1,4,3,0.25,-4
make mesh from object 1,1
delete object 1 : make object 1,1,0
color object 1,rgb(255,255,128)
rem Make the caster
make object box 2,1,1,1
position object 2,0,2.0,0
color object 2,rgb(255,0,0)
rem Shadow object
make object 3,1,1
convert object fvf 3,322
set object transparency 3,1
set object texture 3,3,0
rem init camera
ink rgb(255,255,128),0
sync on : sync rate 30
position camera 4,10,-10
point camera 1.5,0.8,0
autocam off
rem loop
do
`
rem move catser
if upkey()=1 then move object 2,0.2
if downkey()=1 then move object 2,-0.2
if leftkey()=1 then move object left 2,0.2
if rightkey()=1 then move object right 2,0.2
if shiftkey()=1 then move object up 2,0.2
if controlkey()=1 then move object down 2,0.2
if chall<2 and returnkey()=1 then rotate object 2,0,object angle y(2)+2,0
if chall=2 and returnkey()=1 then rotate object 2,object angle x(2)+1,object angle y(2)+2,object angle z(2)+3
`
rem update UV+DIFFUSE on polys
gosub _update_uv_of_shadow_object
`
rem User prompt
set cursor 0,0
print "L E E S C H A L L E N G E T W O"
print
print "Use Arrow Keys to Move, SHIFT and CONTROL raise and lower the Caster Object"
if chall=0
print "Press SPACE to view the challenge"
if spacekey()=1
while spacekey()=1 : sync : endwhile
chall=1
endif
else
if chall=1
print "Use the RETURN Key to Y rotate the Caster Object"
print "Press SPACE for bonus challenge"
print
print "The challenge is to modify the Update UV subroutine so that the Y axis"
print "rotation of the caster object also rotates the shadow via the UV data!"
if spacekey()=1 then chall=2
else
print "Use the RETURN Key to rotate the Caster Object in all directions"
print "The bonus challenge is to modify the Update UV subroutine so that the full"
print "rotation of the caster object creates a realistic shadow using UV data only!"
print "The illustration in the corner shows the 'ideal' shadow, which you must"
print "approximate as closely as you can without changing the texture or shadow mesh"
endif
endif
`
rem bonus challenge
if chall=2
if object exist(10)=0
make object cube 10,3 : lock object on 10 : position object 10,9,-5,16
make object cube 11,3 : lock object on 11 : position object 11,9,-8,16
set object ambient 10,0 : color object 10,rgb(255,0,0)
endif
rotate object 10,object angle x(10)+1,object angle y(10)+2,object angle z(10)+3
make mesh from object 11,10
delete object 11 : make object 11,11,0
lock object on 11 : position object 11,9,-8,16
set object ambient 11,0 : color object 11,0
scale object 11,100,1,100
center text 545,270,"BONUS CHALLENGE"
endif
`
rem update
sync
`
rem end loop
loop
_update_uv_of_shadow_object:
`
rem uses XYZ of target object
x#=object position x(2)
z#=object position z(2)
rem get the object y angle
angy# = object angle y(2)
perc10#=object position y(2)-1.0
if perc10#<0.0 then perc10#=0.0
if perc10#>10.0 then perc10#=10.0
size#=3.0-((2.0/10.0)*perc10#)
diff as DWORD
diff=(255-(25.5*perc10#))<<24
diff=(diff<<24)+(diff<<16)+(diff<<8)+(diff)
`
rem could simplify this, except to demostrate the formation of the matrix
m00# = cos(angy#) : m01# = -sin(angy#)
m10# = sin(angy#) : m11# = cos(angy#)
`
rem update UV data
lock vertexdata for limb 3,0,1
polynum=get vertexdata vertex count()/3
for p=0 to polynum-1
`
rem which poly
vo=p*3
`
rem Get polygon vertices
x0#=get vertexdata position x(vo+0)
z0#=get vertexdata position z(vo+0)
x1#=get vertexdata position x(vo+1)
z1#=get vertexdata position z(vo+1)
x2#=get vertexdata position x(vo+2)
z2#=get vertexdata position z(vo+2)
`
rem Work out UV-coords from Polygon Vs XY-coords
u0# = (x0#-x#)*size#*0.25+0.5 : v0# = (z0#-z#)*size#*0.25+0.5
u1# = (x1#-x#)*size#*0.25+0.5 : v1# = (z1#-z#)*size#*0.25+0.5
u2# = (x2#-x#)*size#*0.25+0.5 : v2# = (z2#-z#)*size#*0.25+0.5
difx# = (u0#-0.5)*m00# + (v0#-0.5)*m01# + 0.5
dify# = (u0#-0.5)*m10# + (v0#-0.5)*m11# + 0.5
u0#=difx# : v0# = dify#
difx# = (u1#-0.5)*m00# + (v1#-0.5)*m01# + 0.5
dify# = (u1#-0.5)*m10# + (v1#-0.5)*m11# + 0.5
u1#=difx# : v1# = dify#
difx# = (u2#-0.5)*m00# + (v2#-0.5)*m01# + 0.5
dify# = (u2#-0.5)*m10# + (v2#-0.5)*m11# + 0.5
u2#=difx# : v2# = dify#
`
rem write UV and DIFFUSE data
set vertexdata uv vo+0,u0#,v0#
set vertexdata uv vo+1,u1#,v1#
set vertexdata uv vo+2,u2#,v2#
set vertexdata diffuse vo+0,diff
set vertexdata diffuse vo+1,diff
set vertexdata diffuse vo+2,diff
`
rem Next polygon
next p
unlock vertexdata
`
return
As for the bonus, I can imagine it would be very difficult to distort the texture so much using only the UV co-ordinates, individual axes are possible, but not all combined. So that bit's got me stumped.