Chapter-45: Curl detector
Note: It runs faster offline.
Script
#--------------------------------------------------#
# Define lists for fields, names and text
#--------------------------------------------------#
Ltxt = {"curl=<0,0,0>", "curl=<0,0,2>", "curl=<0,0,2x/(x^2+1)-2y/(y^2+1)>", "curl=<0, 0, 1/y^2-1/x^2>", "curl=<0,0,0>", "curl=<0,0,1-cos(y)>", "curl=<0,0,2>", "curl=<0,0,0>"}
LFx = {1.5x + 0*y, 0*x - 1.5y, 0*x + 1.5ln(1+y^2), 0*x + 1/y, -4y/(x^2+y^2)+0*y, 1.5sin(y)+ 0*x, x-y + 0*x, 1.5x + 0*y}
LFy = {0*x + 1.5y, 1.5x + 0*y, 1.5ln(1+x^2) + 0*y, 1/x + 0*y, 4x/(x^2+y^2)+0*x, 1.5x + 0*y, x+y + 0*y, -1.5y + 0*x}
Lname = {"", "<-y,x>", "", "<1/y,1/x>", "<-y/r^2,x/r^2>", "", "", ""}
SetCaption(Lname, "Field:=")
ind = SelectedIndex( Lname )
#------------------------------------#
# Define field components
#------------------------------------#
F1 = Element(LFx, ind)
F2 = Element(LFy, ind)
#-------------------#
# Define limits
#-------------------#
xmin = -4
xmax = 4
ymin = -4
ymax = 4
#-------------------#
# Auxiliar list
#-------------------#
LN = 1...10
#---------------------------------------------#
# Define random position of points
#---------------------------------------------#
Execute(Zip(" XP"+k+" = RandomUniform( xmin, xmax ) ", k, LN))
Execute(Zip(" YP"+k+" = RandomUniform( ymin, ymax ) ", k, LN))
#-------------------#
# Define points
#-------------------#
Execute(Zip(" P"+k+" = ( XP"+k+", YP"+k+" ) ", k, LN))
Execute(Zip(" ShowLabel( P"+k+", false ) ", k, LN))
#-------------------#
# Define velocity
#-------------------#
Execute(Zip(" VXP"+k+" = F1( P"+k+" ) ", k, LN))
Execute(Zip(" VYP"+k+" = F2( P"+k+" ) ", k, LN))
#----------------------------------#
# Set slider for animation
#----------------------------------#
animate = false
SetCaption(animate, "Run")
speed = 1
Run = Slider(-5, 5, 0.01, speed, 140, false, true, false, false)
SetVisibleInView(Run, 1, false)
#-----------------------------------------------#
# Define curl lists, values and angles
#-----------------------------------------------#
Execute(Zip(" curlList"+k+" = { 0, 2, 2*x(P"+k+")/(x(P"+k+")^2+1) - 2*y(P"+k+") /(y(P"+k+")^2+1), 1/y(P"+k+")^2 - 1/x(P"+k+")^2, 0, 1-cos(y(P"+k+")), 2, 0} ", k, LN))
Execute(Zip( " curlValue"+k+" = Element(curlList"+k+", ind) ", k, LN))
Execute(Zip( "curlAngle"+k+" = Slider(0, 2pi, 0.01, curlValue"+k+", 200, false, true, false, false)", k, LN))
Execute(Zip( " SetVisibleInView(curlAngle"+k+", 1, false) ", k, LN))
curlText = Element(Ltxt, ind)
#--------------------------------------------------------------#
# Define spokes for points to represent the curl
#--------------------------------------------------------------#
Execute(Zip(" spoke"+k+" = Sequence(Segment(Rotate(P"+k+" - (0.4, 0), j + curlAngle"+k+", P"+k+"), Rotate(P"+k+" + (0.4, 0), j + curlAngle"+k+", P"+k+")), j, 0, 2.0944, 1.0472)", k, LN))
back = Polygon((-4,-4), (4, -4), (4, 4), (-4,4))
#Set inverse filling for this polygon and no seleciton allowed#
#After creating the slider "Run" add these lines to the "OnUpdate" tab#
#Update location
Execute(Zip(" SetValue(XP"+k+", XP"+k+" + 0.01*VXP"+k+") ", k, LN))
Execute(Zip(" SetValue(YP"+k+", YP"+k+" + 0.01*VYP"+k+") ", k, LN))
#Check edges
Execute(Zip(" If( x(P"+k+")>=xmax, SetValue( XP"+k+", RandomUniform( xmin, xmax ) ), If( x(P"+k+")<=xmin, SetValue( XP"+k+", RandomUniform( xmin, xmax ) ) ) ) ", k, LN))
Execute(Zip(" If( y(P"+k+")>=ymax, SetValue( YP"+k+", RandomUniform( ymin, ymax ) ), If( y(P"+k+")<=ymin, SetValue( YP"+k+", RandomUniform( ymin, ymax ) ) ) ) ", k, LN))
#---------------------------------------------------------------#
# Vector field image for each example was made with this applet:
# https://www.geogebra.org/m/cXgNb58T
#---------------------------------------------------------------#