function calcCapelet(){
/* @copyright 2004 Lucia Liljegren*/

pester = document.location;
p =document.capeForm;

expireDate = new Date;
expireDate.setMonth(expireDate.getMonth()+6);
username = pester;

document.cookie="pester=" + username + "expires="+ expireDate.toGMTString(); 

if(document.cookie ==""){
/* @copyright 2004 Lucia Liljegren
*/

    alert("Please set your browser to accept cookies. You must accept cookies to run this page.");
}
else {
    pesterZero=document.cookie.split("/")[0];  //figure out if local or away.    
    pesterRead = document.cookie.split("/")[4];
    pesterAway=document.cookie.split("/")[2];    
}
pester = "yes";
    if(pesterZero == "pester=file" || pesterRead =="lucia"){pester="no"}
else if(pesterZero == "pester=http:" || pesterAway == "www.thedietdiary.com"){pester="no"}
 
else{ pester = "yes"; 
   p.mainStIn.value=0.01;
    p.mainRowIn.value=0.01;
    alert(" Please run my programs from my site at www.thedietdiary.com!"  ) } ;
//===================
if(pester == "no"){
/* @copyright 2004 Lucia Liljegren*/

    var shoulderDrop = 1;

    // mimic other code as much as possible.
    
    if(eval(p.mainStIn.value) < 0.00001) {p.mainStIn.value = 0.001; }
    if(eval(p.mainRowIn.value) < 0.00001) {p.mainRowIn.value = 0.001; }
    
     numTrap=8.
     // I tested. 330 is just a bit too small for the total  angle. 
     // my green with pink I cord collar is 8* 30 + 2*45 = 240 + 90 = 330.
     // it  doesn't open up *quite* fast enough over the shoulders. 
     //360 would be table cloth like.
     //  So, I'm going to make totalAngleDeg = 340 as the target. 
     totalAngleDeg=340; // total angle to lie flat on shoulders.
     ponchoAngleDeg=240; // test
     
    baseThetaDeg= ponchoAngleDeg/numTrap;
    realThetaDeg=baseThetaDeg; // this will be changed when I do more calculations. It is affected by the stitch/row gauge ratio,
    shoulderAngleDeg= (totalAngleDeg - numTrap*realThetaDeg)/2;
    
    totalAngleRad=totalAngleDeg*Math.PI/180
    realThetaRad=realThetaDeg * Math.PI/180;   // this is the angle of the shaping (turning) darts
    ShoulderAngleRad=shoulderAngleDeg * Math.PI/180;
    ponchoAngleRad = ponchoAngleDeg*Math.PI/180

//  Calculate needles from center of imaginary circle to shoulder edge.
    shoulderWidth=eval(p.shoulderWidth.value)
    shiftNeedle=Math.round(p.shiftNeedle.value);
    p.shiftNeedle.value = shiftNeedle
    
    neckOpening=eval(p.neckOpening.value);
    ovalFactor = 0 // I shouldn't need this if I calculate things correctly.
    lengthDartsContribution= divide(numTrap*2,p.mainRowIn.value);// need this added to neck lenght
    lengthOfEight=divide(8,p.mainRowIn.value); // this is to try to keep beginning from ever being -2 due to cumulative rounding. (There is a certain randomness to roudning. This is two at cast on and bind off, then two at the end.
    
    b = (neckOpening-lengthDartsContribution-lengthOfEight)/(4* ovalFactor +  2*Math.tan(realThetaRad/2)*(numTrap+2))// I want two "circles" on the edge of a square.  This worked with my newspaper. I need to scale by the num trap+2 because I realy knit this many num traps!    
    innerRadius= b 
    trapWidth= b*(2*Math.tan(realThetaRad/2))
    neckWidth = 2*(trapWidth + trapWidth*Math.cos(realThetaRad) + trapWidth*Math.cos(2*realThetaRad) ) + lengthOfEight 
    //alert( b + " | "  + 2* b + " < " + neckWidth ) // first is flat, second included, third more, then that extra length of eight. It will be this lenght-- other htan rounding.
    /*
    flatNeckWidth= b  // this should work because the perimeter is 2*b + radius * AngleOfCirccles
    neckWidth=  2*innerRadius +  flatNeckWidth;
    ratio = flatNeckWidth/neckWidth
    ratioRad =innerRadius/neckWidth
    //alert( ratio + " : " +  ratioRad ) // I think I want ratio near 1/3 based on my paper cut out neck
   
    */
    outerRadius= 0.5* shoulderWidth/Math.cos(ShoulderAngleRad/2);

// Estimate number of rows over the inner radius
	estRowsInner= 2*Math.round(mult(innerRadius*ponchoAngleRad,p.mainRowIn.value)/2);
	shapeRowsInner = estRowsInner- numTrap*2;  // excludes the 2 rows for darts.
	dropFraction=0.75;
	neckDif=dropFraction*innerRadius; // the back will rise  this much, the front will drop this much.
	
	halfRows=shapeRowsInner
	sitchInc=Math.round(mult(neckDif,p.mainStIn.value)) // 
	//alert(halfRows +" = rows  halfway excluding darts " + sitchInc + "stitches : " );
	
// find widths of top of all trapezoids.

widthTopTrap = new Array
rowsTopTrap = new Array
radiusBegTrap =new Array
radiusEndTrap= new Array
centerRadTrap = new Array
needlesBegTrap = new Array
needlesEndTrap = new Array
incNeedlesTrap = new Array
distAround = new Array

numTurningDarts= numTrap/2;
numIncTraps= numTurningDarts;
sizeArray = numTurningDarts + 1


shoulderArray= numIncTraps/2;  // because in the middle, and first array value is zero.
msg = "start: innerRadius " + innerRadius + ",  neckDif = " + neckDif + " shoulder" + shoulderArray;


// try log-------------------------------------------------------
// need a monotonically *decreasing* function of "i".
// need to result ina total change of neckdif from front to back.  So, goes from zero to 1.
// need zero at shoulder.

adjShould= Math.sqrt( ( sizeArray - shoulderArray )/sizeArray ) 

 
for( i=0; i < sizeArray+1; i++){  // more array nodes to give values for beg. and end.
     count = i;
    if(i <= shoulderArray){ distAround[i]=   i   /(numTurningDarts)  }// -1 because I skip one!
    else{	            distAround[i]=  (i-1)/(numTurningDarts)  }     
}
half=3/4  // 1 is linear.  square root over corrects. So, I'm going for 3/4
adjust= Math.exp( half*Math.log(distAround[shoulderArray]))  // to make zero at shoulder
for( i=0; i < sizeArray+1; i++){  // more array nodes to give values for beg. and end.
     count = i;
    radiusBegTrap[i]=   innerRadius -neckDif* (  Math.exp(half*Math.log(distAround[i]) ) - adjust );
   //alert("i"+ i + "dist = " + distAround[i] + "- " +distAround[shoulderArray] + "  =" + radiusBegTrap[i]) 
      
    }


resultantNeckdif = radiusBegTrap[0]-radiusBegTrap[sizeArray]
msg = "    targetNeckDif" + neckDif + " inches  ==>  "+resultantNeckdif + "inches"
//alert(msg);
 
// end log----------------------------------------

// ------------------
totalInnerCircCircumf= 0;
totalStitchesIncreased = 0;

flatAdjust = (neckWidth-2*innerRadius)/2;

for( i=0; i < sizeArray; i++){  // more array nodes to give values for beg. and end.


    centerRadTrap[i] = (radiusBegTrap[i+1]+radiusBegTrap[i])/2;  // average
    widthTopTrap[i] = 2* centerRadTrap[i] * Math.tan(realThetaRad/2);
    rowsTopTrap[i] =2* Math.round( mult(widthTopTrap[i] , p.mainRowIn.value)/2);
    widthTopTrap[i]=divide(rowsTopTrap[i],p.mainRowIn.value) // exact.
    needlesBegTrap[i]= Math.round(mult((outerRadius-radiusBegTrap[i]), p.mainStIn.value) );// too many
    needlesEndTrap[i]= Math.round(mult((outerRadius-radiusBegTrap[i+1]), p.mainStIn.value) ); // too many
    
    needlesBegTrap[i]= Math.round(mult((outerRadius-radiusBegTrap[i])-flatAdjust, p.mainStIn.value) );// should correct
    needlesEndTrap[i]= Math.round(mult((outerRadius-radiusBegTrap[i+1])-flatAdjust, p.mainStIn.value) ); // should correct
    
    
    incNeedlesTrap[i]=needlesEndTrap[i] - needlesBegTrap[i];
    if(i<sizeArray){  // the last array index was a fake place  holder.
	totalInnerCircCircumf+= widthTopTrap[i];
	totalStitchesIncreased +=incNeedlesTrap[i]}
}


totalInnerCircCircumf += (numTurningDarts+1) * divide(2,p.mainRowIn.value);
totalInnerCircCircumf = 2*totalInnerCircCircumf;
//alert("totalInnerCircCircum =" + totalInnerCircCircumf + "neckCirc= " +neckOpening  + " totalStitchesIncreased= " + totalStitchesIncreased);

// this is the extra to add just after cast on and before bind off..  It is added in four places. 
widthExtra = divide(neckOpening -totalInnerCircCircumf,4);  
rowsExtra=2*Math.round( mult(widthExtra, p.mainRowIn.value)/2);
p.firstRows.value = rowsExtra;
p.lastRows.value = rowsExtra;

castOn =needlesBegTrap[0];
p.castOn.value=castOn;
// calculate the first trapezoid.

p.stitchIncTrap1.value = incNeedlesTrap[0];
p.rowsTrap1.value = rowsTopTrap[0];
p.widthTrap1.value=widthTopTrap[0];
p.needlesBegTrap1.value=needlesBegTrap[0]

rowsBetweenInc = Math.floor(divide(rowsTopTrap[0],incNeedlesTrap[0]));
//alert(" : " + rowsTopTrap[0] + " / " +incNeedlesTrap[0] + " = "+ rowsBetweenInc ) 
rectangle1 = new Rectangle(incNeedlesTrap[0],rowsTopTrap[0],widthTopTrap[0],needlesBegTrap[0]);

extraRows= 		rectangle1.extraRows
p.rowsBetweenInc1.value=rectangle1.rowsBetween
rowDif = 		rectangle1.rowDif
p.preRows1.value=	extraRows-rowDif;
p.postRows1.value=  	rowDif;

p.numTrapRepeats1.value=incNeedlesTrap[0]-1
p.stitchesAfter1.value=needlesBegTrap[1];


//second
p.stitchIncTrap2.value = incNeedlesTrap[1];
p.rowsTrap2.value = rowsTopTrap[1];
p.widthTrap2.value=widthTopTrap[1];
p.needlesBegTrap2.value=needlesBegTrap[1]

rectangle2 = new Rectangle(incNeedlesTrap[1],rowsTopTrap[1],widthTopTrap[1],needlesBegTrap[1]);

extraRows= 		rectangle2.extraRows
p.rowsBetweenInc2.value=rectangle2.rowsBetween
rowDif = 		rectangle2.rowDif
p.preRows2.value=	extraRows-rowDif;
p.postRows2.value=  	rowDif;

p.numTrapRepeats2.value=incNeedlesTrap[1]-1
p.stitchesAfter2.value=needlesBegTrap[2];



// third is shoulder
p.rowsTrapShoulderHalf1.value= 2*Math.ceil(rowsTopTrap[2]/4)
p.rowsTrapShoulderHalf2.value= sub(rowsTopTrap[2],p.rowsTrapShoulderHalf1.value)

//fourth (Called third in text.)
p.stitchIncTrap4.value = incNeedlesTrap[3];
p.rowsTrap4.value = rowsTopTrap[3];
p.widthTrap4.value=widthTopTrap[3];
p.needlesBegTrap4.value=needlesBegTrap[3]

rectangle4 = new Rectangle(incNeedlesTrap[3],rowsTopTrap[3],widthTopTrap[3],needlesBegTrap[3]);

extraRows= 		rectangle4.extraRows
p.rowsBetweenInc4.value=rectangle4.rowsBetween
rowDif = 		rectangle4.rowDif
p.preRows4.value=	extraRows-rowDif;
p.postRows4.value=  	rowDif;

p.numTrapRepeats4.value=incNeedlesTrap[3]-1
p.stitchesAfter4.value=needlesBegTrap[4];


//fifth
p.stitchIncTrap5.value = incNeedlesTrap[4];
p.rowsTrap5.value = rowsTopTrap[4];
p.widthTrap5.value=widthTopTrap[4];
p.needlesBegTrap5.value=needlesBegTrap[4]

rectangle5 = new Rectangle(incNeedlesTrap[4],rowsTopTrap[4],widthTopTrap[4],needlesBegTrap[4]);

extraRows= 		rectangle5.extraRows
p.rowsBetweenInc5.value=rectangle5.rowsBetween
rowDif = 		rectangle5.rowDif
p.preRows5.value=	extraRows-rowDif;
p.postRows5.value=  	rowDif;

p.numTrapRepeats5.value=incNeedlesTrap[4]-1
p.stitchesAfter5.value = needlesEndTrap[4];
// calculate short rows
turningWedge();
shoulderWedge();


//============================

ratioBackToFront= widthTopTrap[0]/widthTopTrap[4]
//alert("dropFraction " + dropFraction + " results in a ratio of " + ratioBackToFront);

totalNeedles=needlesEndTrap[sizeArray-1];
p.maxStitches.value=totalNeedles;
p.minNeck.value = Math.round(divide(numTrap * 8,p.mainRowIn.value)*10)/10  // this isn't the best way to do it.

    
    p.leftNeedle.value= shiftNeedle-Math.round(totalNeedles/2);
    p.rightNeedle.value = add(p.leftNeedle.value,totalNeedles); 
    p.leftNeedle2.value=p.leftNeedle.value
    p.rightNeedle2.value=p.rightNeedle.value
    p.incStitches.value = totalStitchesIncreased;
    
    p.mark1.value= 2* castOn
    
p.tooFewStitches.value = "Thanks for running this from lucia's site. I'll fill the boxes now!" ;
}

else {
     alert(" Please run my programs from my site at www.thedietdiary.com!"  )
    alert("Sorry! I didn't fill the boxes. Please run this page from my site at www.thedietdiary.com!")
    p.tooFewStitches.value = "Please run this from lucia's site!  I'm not filling the result boxes.  ("+pesterZero +" : "+ pesterAway+" : "+pesterRead +")";
    p.mainStIn.value=0.01;
    p.mainRowIn.value=0.01;
}

}

/* 
@copyright 2004 Lucia Liljegren */
//================================================================================================
// write function to calculate the number before, the number between etc.
function Rectangle(incNeedles,rowsTop,widthTop,needlesBeg){

rowsBetween = Math.floor(divide(rowsTop,incNeedles));
extraRows= rowsTop- rowsBetween * incNeedles;
rowDif = Math.max(Math.round((extraRows-rowsBetween)/2),0)
preRows=extraRows-rowDif;
postRows=  rowDif;
numTrapRepeats=incNeedles-1
stitchesAfter=needlesBeg;


// set into hash
this.rowsBetween=rowsBetween
this.extraRows= extraRows
this.rowDif = rowDif
this.preRows=preRows
this.postRows= postRows
this.numTrapRepeats=numTrapRepeats
this.stitchesAfter=stitchesAfter

//
p.neckNeedles.value =Math.round( mult(neckOpening,p.mainStIn.value))

// warnings
// -- if any of the rectangles have less than one increase.
// -- if beginning pad has less than-4 rows. (-2 might be rounding.)
// -- if any rectangle has fewer than 2 rows.
// 

}
//================================================
function turningWedge(){

// I should pass realThetaRad  That's the only variabe I  ned.

// work out ideal number of stitches to take out of work per 12 rows knit while turning for cape.
    turnRowsTotal=6
	var idealStitchesTurn = Math.round(divide(p.mainStIn.value,p.mainRowIn.value) * turnRowsTotal / Math.tan(realThetaRad/2) )  // divide by two because each wedge takes out half.
	p.turnNeedleTotal.value=turnNeedleTotal= idealStitchesTurn;
	p.turnRowsTotal.value=turnRowsTotal;
	var turnOperations=turnRowsTotal/2;
	
	 lowNeedles=Math.floor(divide(idealStitchesTurn,turnOperations));
	 highNeedles=lowNeedles+1;
	
	 timesHigh=idealStitchesTurn%turnOperations;
	 timesLow=turnOperations - timesHigh
    
    // reset turn rows so instructions will be out of six not 12
    //   later on, code to permit an every 4 rows repeat if the angle matches better that way.
    p.skipTurn.value="repeat";
    p.lowNeedles.value=lowNeedles;
    p.highNeedles.value=highNeedles;  // this is the possibly repeated value.
    p.highNeedles2.value=highNeedles; // always.
    
    if(timesHigh == 0) {  // nothing repeated.
	p.lowNeedles.value=lowNeedles ;
	p.highNeedles.value=lowNeedles;
    }
    else if(timesHigh==1) {
	p.lowNeedles.value=highNeedles;
	p.highNeedles.value=lowNeedles;
    }
 // this stuff belongs outside function.   
    //figure row count.
    p.rowsTurnDart1.value = rowsTurnDart(p.stitchesAfter1.value,idealStitchesTurn,turnRowsTotal);    
    p.rowsTurnDart2.value = rowsTurnDart(p.stitchesAfter2.value,idealStitchesTurn,turnRowsTotal);// just before shoulder
    p.rowsTurnDart3.value = rowsTurnDart(p.stitchesAfter2.value,idealStitchesTurn,turnRowsTotal); // just after shoulder
    p.rowsTurnDart4.value = rowsTurnDart(p.stitchesAfter4.value,idealStitchesTurn,turnRowsTotal); 
    p.rowsTurnDartAfter1.value = 2*(eval(p.rowsTurnDart1.value)-1);
    p.rowsTurnDartAfter2.value = 2*(eval(p.rowsTurnDart2.value)-1);
    p.rowsTurnDartAfter3.value = 2*(eval(p.rowsTurnDart3.value)-1);
    p.rowsTurnDartAfter4.value = 2*(eval(p.rowsTurnDart4.value)-1);
    
    // recalculate real theta and real shoulder angle.
    tanRealTheta =  divide(turnRowsTotal,p.mainRowIn.value)/divide(idealStitchesTurn,p.mainStIn.value);
    realThetaRad = 2* Math.atan(tanRealTheta);
    realThetaDeg= realThetaRad*180/Math.PI;
 //alert(" compare thetas " + realThetaDeg + " :" + baseThetaDeg)

}
/////  Right now I have these written in a way that I must call the function that figures out how manyrows inside a wedge function
function shoulderWedge(){
	turnRowsTotal=6
	shoulderAngleDeg= (totalAngleDeg - numTrap*realThetaDeg)/2;
	shoulderAngleRad = shoulderAngleDeg*Math.PI/180;
	
	 idealStitchesTurn = Math.round(divide(p.mainStIn.value,p.mainRowIn.value) * turnRowsTotal / Math.tan(shoulderAngleRad/2) )
	//p.turnNeedleTotal.value=turnNeedleTotal= idealStitchesTurn;
	//p.turnRowsTotal.value=turnRowsTotal;
	 turnOperations=turnRowsTotal/2;
	
	 lowNeedles=Math.floor(divide(idealStitchesTurn,turnOperations));
	 highNeedles=lowNeedles+1;
	
	timesHigh=idealStitchesTurn%turnOperations;
	timesLow=turnOperations - timesHigh
	
	 // reset turn rows so instructions will be out of six not 12
    //   later on, code to permit an every 4 rows repeat if the angle matches better that way.
    p.skipTurnSh.value="repeat";
    p.lowNeedlesSh.value=lowNeedles;
    p.highNeedlesSh.value=highNeedles;  // this is the possibly repeated value.
    p.highNeedles2Sh.value=highNeedles; // always.
    
    if(timesHigh == 0) { 
	p.lowNeedlesSh.value=lowNeedles ;
	p.highNeedlesSh.value=lowNeedles;
    }
    else if(timesHigh==1) {
	p.lowNeedles.value=highNeedles;
	p.highNeedles.value=lowNeedles;
    }
 // this stuff belongs outside function.   
    //figure row count.
    p.rowsDartSh.value = rowsTurnDart(p.stitchesAfter2.value,idealStitchesTurn,turnRowsTotal);// just before shoulder
    p.rowsDartShAfter.value = 2*(eval(p.rowsDartSh.value)-1);
    p.shoulderNeedleTotal.value=turnNeedleTotal= idealStitchesTurn;
    p.shoulderRowsTotal.value=turnRowsTotal;
    
    tanRealBeta =  divide(turnRowsTotal,p.mainRowIn.value)/divide(idealStitchesTurn,p.mainStIn.value);
    realBetaRad = 2* Math.atan(tanRealBeta);
    realBetaDeg= realBetaRad*180/Math.PI;

    //alert(" compare shoulder Angles (target) " + realBetaDeg + " :" + shoulderAngleDeg)
}

//=====================================================
function rowsTurnDart(stitches, stitchesPerBlock, turnRows){
    var numComplete = Math.floor(divide(stitches,stitchesPerBlock));
    var extraLeft = sub(stitches,numComplete*stitchesPerBlock)
   
    // there are 1 or 2 extra passees left.
    if(extraLeft==0){extraPass=0}
    else if( extraLeft < highNeedles){extraPass=1}
    else {extraPass=2}
    
   var rowsTurnDart = numComplete*turnRows + 2*extraPass - 1
   return rowsTurnDart;
 
} 
