#!/bin/sh # MetaCard 2.4 stack # The following is not ASCII text, # so now would be a good time to q out of more exec mc $0 "$@" @{ Graph & table objects Äon preOpenStack # In case this has been opened on a new type of computer from that on which it was # created, or a font is missing, redraw the objects showing initially. lock screen click at the loc of button "Example 2" set the lockRecent to true set the lockMessages to true go to card "table object" click at the loc of button "Example 1" go to card 1 unlock screen set the lockRecent to false set the lockMessages to false pass preOpenStack end preOpenStack on openCard # If the user moved between cards with the arrow key, set the tabbed menu button group appropriately. set the menuHistory of btn "which object" to (the number of this card) pass openCard end openCard w ÜÜÜÜÜÜ ’’’’’’ white ¬¬¬¬¬¬ ¬¬¬¬¬¬ f Č wdata2columnwidths s110 154 175 191 226 75 122 166 176 268 189 199 199 181 191 191 115 157 169 179 179 102 75 153 224 236 190 151 109 75 121 128 128 139 203 227 175 217 108 194 176 117 174 199 153 181 200 114 199 145 234 191 191 75 99 75 181 272 245 267 254 264 264 231 241 241 203 239 249 249 225 256 219 229 229 161 265 183 257 167 158 202 152 162 162 204 214 214 102 173 165 240 246 242 166 176 176 155 206 181 100 144 163 208 121 75 101 173 161 75 183 137 196 183 142 113 75 142 166 146 173 133 136 165 175 175 205 214 75 213 223 223 185 208 218 218 126 202 232 91 133 187 161 220 270 270 242 145 237 238 238 142 142 142 130 172 129 136 136 147 134 196 119 163 147 218 220 255 240 212 222 222 211 161 149 252 223 253 225 159 125 176 75 141 148 148 159 200 150 200 190 178 132 101 122 237 269 240 205 131 118 128 128 158 216 90 161 153 154 164 164 88 121 142 95 137 170 177 162 75 126 227 189 175 163wdata1data ä17.87 4.309e+11 269.3 6.650e+10 29.11 0.1838 1.600e+9 2.000e+12 90.00 18.39 4.405e+11 273.9 6.880e+10 29.34 0.1744 1.608e+9 2.000e+12 89.15 19.01 4.471e+11 276.0 7.161e+10 29.45 0.1690 1.620e+9 1.999e+12 89.15 19.61 4.530e+11 277.3 7.449e+10 29.52 0.1658 1.633e+9 1.999e+12 89.36 20.19 4.587e+11 278.4 7.737e+10 29.57 0.1640 1.648e+9 1.999e+12 89.74 20.73 4.646e+11 279.3 8.020e+10 29.61 0.1630 1.663e+9 1.998e+12 90.23 21.28 4.705e+11 280.3 8.307e+10 29.66 0.1625 1.679e+9 1.998e+12 90.92 21.83 4.766e+11 281.3 8.600e+10 29.71 0.1624 1.694e+9 1.998e+12 91.80 22.38 4.828e+11 282.4 8.900e+10 29.76 0.1626 1.710e+9 1.997e+12 92.84 22.95 4.891e+11 283.5 9.207e+10 29.82 0.1631 1.725e+9 1.997e+12 94.03 23.53 4.956e+11 284.8 9.523e+10 29.88 0.1639 1.740e+9 1.997e+12 95.35 24.12 5.024e+11 286.1 9.847e+10 29.95 0.1649 1.756e+9 1.996e+12 96.79 24.72 5.093e+11 287.5 1.018e+11 30.02 0.1663 1.771e+9 1.996e+12 98.33 25.34 5.164e+11 289.1 1.053e+11 30.11 0.1679 1.787e+9 1.995e+12 99.96 25.97 5.241e+11 290.8 1.089e+11 30.20 0.1699 1.802e+9 1.995e+12 101.7 26.63 5.320e+11 292.7 1.126e+11 30.31 0.1723 1.818e+9 1.994e+12 103.5 27.30 5.401e+11 294.6 1.164e+11 30.41 0.1749 1.833e+9 1.994e+12 105.4 27.99 5.483e+11 296.6 1.204e+11 30.52 0.1779 1.849e+9 1.993e+12 107.4 28.71 5.568e+11 298.6 1.245e+11 30.64 0.1813 1.865e+9 1.993e+12 109.4 29.44 5.653e+11 300.6 1.288e+11 30.75 0.1850 1.881e+9 1.992e+12 111.5 30.20 5.741e+11 302.6 1.332e+11 30.87 0.1890 1.897e+9 1.992e+12 113.7 30.97 5.831e+11 304.8 1.378e+11 31.00 0.1934 1.913e+9 1.991e+12 115.9 31.77 5.923e+11 306.9 1.426e+11 31.13 0.1982 1.930e+9 1.991e+12 118.3 32.59 6.018e+11 309.2 1.475e+11 31.27 0.2033 1.946e+9 1.990e+12 120.7 33.44 6.115e+11 311.5 1.527e+11 31.41 0.2087 1.963e+9 1.989e+12 123.1 34.31 6.216e+11 313.8 1.580e+11 31.55 0.2145 1.981e+9 1.989e+12 125.7 35.20 6.319e+11 316.3 1.636e+11 31.70 0.2206 1.998e+9 1.988e+12 128.3 36.12 6.425e+11 318.7 1.693e+11 31.86 0.2271 2.016e+9 1.987e+12 130.9 37.06 6.535e+11 321.3 1.753e+11 32.02 0.2340 2.034e+9 1.987e+12 133.7 38.02 6.647e+11 323.9 1.815e+11 32.19 0.2412 2.052e+9 1.986e+12 136.5 39.02 6.763e+11 326.6 1.879e+11 32.36 0.2488 2.071e+9 1.985e+12 139.4 40.03 6.883e+11 329.4 1.946e+11 32.54 0.2567 2.090e+9 1.984e+12 142.4 41.08 7.007e+11 332.2 2.015e+11 32.73 0.2650 2.109e+9 1.984e+12 145.4 42.15 7.134e+11 335.1 2.087e+11 32.92 0.2736 2.129e+9 1.983e+12 148.5 43.24 7.265e+11 338.0 2.162e+11 33.12 0.2826 2.149e+9 1.982e+12 151.7 44.37 7.401e+11 341.0 2.239e+11 33.32 0.2921 2.170e+9 1.981e+12 155.0 45.52 7.541e+11 344.1 2.320e+11 33.53 0.3019 2.191e+9 1.980e+12 158.3 46.69 7.685e+11 347.3 2.403e+11 33.75 0.3121 2.213e+9 1.979e+12 161.7 47.90 7.834e+11 350.5 2.490e+11 33.97 0.3227 2.235e+9 1.978e+12 165.2 49.13 7.987e+11 353.8 2.580e+11 34.20 0.3337 2.258e+9 1.977e+12 168.8 50.39 8.146e+11 357.1 2.673e+11 34.44 0.3452 2.281e+9 1.976e+12 172.4 51.48 8.309e+11 359.1 2.770e+11 41.40 0.3571 2.314e+9 1.975e+12 175.5 52.40 8.488e+11 360.4 2.870e+11 41.64 0.3694 2.355e+9 1.973e+12 178.1 53.35 8.675e+11 362.0 2.973e+11 41.91 0.3823 2.396e+9 1.972e+12 180.7 54.33 8.867e+11 363.8 3.079e+11 42.19 0.3956 2.437e+9 1.971e+12 183.5 55.32 9.064e+11 365.6 3.189e+11 42.47 0.4094 2.479e+9 1.970e+12 186.4 56.32 9.266e+11 367.5 3.303e+11 42.77 0.4237 2.521e+9 1.968e+12 189.4 57.35 9.474e+11 369.5 3.420e+11 43.08 0.4385 2.564e+9 1.967e+12 192.4 58.39 9.687e+11 371.5 3.541e+11 43.40 0.4539 2.608e+9 1.965e+12 195.5 59.45 9.906e+11 373.5 3.666e+11 43.73 0.4699 2.652e+9 1.964e+12 198.6 60.52 1.013e+12 375.6 3.796e+11 44.06 0.4865 2.697e+9 1.962e+12 201.8 61.61 1.036e+12 377.8 3.930e+11 44.41 0.5037 2.743e+9 1.961e+12 205.0 62.71 1.060e+12 380.0 4.068e+11 44.76 0.5215 2.790e+9 1.959e+12 208.3 63.83 1.084e+12 382.2 4.212e+11 45.12 0.5400 2.837e+9 1.957e+12 211.6 64.96 1.109e+12 384.5 4.360e+11 45.50 0.5591 2.886e+9 1.955e+12 215.0 66.11 1.136e+12 387.1 4.513e+11 45.90 0.5790 2.935e+9 1.953e+12 218.4 67.27 1.164e+12 389.8 4.671e+11 46.33 0.5996 2.986e+9 1.952e+12 221.8 68.45 1.192e+12 392.5 4.835e+11 46.75 0.6209 3.037e+9 1.950e+12 225.3 69.65 1.221e+12 395.2 5.005e+11 47.18 0.6429 3.090e+9 1.947e+12 228.9 70.86 1.250e+12 397.7 5.180e+11 47.62 0.6657 3.144e+9 1.945e+12 232.4 72.08 1.280e+12 400.3 5.362e+11 48.06 0.6893 3.199e+9 1.943e+12 236.1 73.32 1.311e+12 402.7 5.550e+11 48.50 0.7138 3.255e+9 1.941e+12 239.7 74.57 1.342e+12 405.1 5.744e+11 48.95 0.7391 3.312e+9 1.938e+12 243.4 75.82 1.374e+12 407.5 5.944e+11 49.41 0.7652 3.371e+9 1.936e+12 247.2 77.09 1.406e+12 409.8 6.151e+11 49.87 0.7923 3.431e+9 1.933e+12 250.9 78.37 1.439e+12 412.0 6.364e+11 50.34 0.8203 3.492e+9 1.931e+12 254.7 79.66 1.469e+12 413.4 6.584e+11 50.77 0.8493 3.554e+9 1.928e+12 258.6 80.96 1.502e+12 415.3 6.810e+11 51.25 0.8792 3.617e+9 1.925e+12 262.5 82.28 1.537e+12 417.5 7.044e+11 51.77 0.9101 3.681e+9 1.922e+12 266.5 83.61 1.572e+12 419.8 7.284e+11 52.31 0.9421 3.746e+9 1.919e+12 270.6 84.96 1.609e+12 422.0 7.532e+11 52.87 0.9751 3.812e+9 1.916e+12 274.7 86.33 1.646e+12 424.2 7.788e+11 53.43 1.009 3.879e+9 1.913e+12 278.8 87.70 1.683e+12 426.3 8.051e+11 53.91 1.045 3.948e+9 1.910e+12 283.1 89.08 1.720e+12 428.3 8.321e+11 54.40 1.082 4.017e+9 1.906e+12 287.5 90.45 1.758e+12 430.2 8.598e+11 54.90 1.121 4.087e+9 1.902e+12 292.1 91.83 1.797e+12 432.1 8.882e+11 55.42 1.162 4.159e+9 1.898e+12 296.8 93.22 1.836e+12 434.0 9.173e+11 55.95 1.204 4.232e+9 1.894e+12 301.6 94.61 1.877e+12 435.9 9.473e+11 56.50 1.248 4.306e+9 1.890e+12 306.5 96.00 1.918e+12 437.8 9.781e+11 57.06 1.294 4.381e+9 1.886e+12 311.4 97.40 1.960e+12 439.6 1.010e+12 57.62 1.342 4.458e+9 1.881e+12 316.4 98.81 2.002e+12 441.4 1.042e+12 58.12 1.393 4.536e+9 1.876e+12 321.4 100.2 2.045e+12 443.0 1.076e+12 58.62 1.445 4.615e+9 1.871e+12 326.6 101.6 2.088e+12 444.6 1.110e+12 59.13 1.501 4.695e+9 1.866e+12 331.7 103.1 2.131e+12 446.1 1.145e+12 59.64 1.559 4.777e+9 1.860e+12 336.9 104.5 2.175e+12 447.5 1.181e+12 60.15 1.620 4.860e+9 1.854e+12 342.2 105.9 2.219e+12 448.9 1.218e+12 60.67 1.684 4.944e+9 1.848e+12 347.5 107.4 2.264e+12 450.2 1.256e+12 61.20 1.751 5.028e+9 1.842e+12 352.9 108.9 2.308e+12 451.3 1.295e+12 61.73 1.821 5.114e+9 1.835e+12 358.3 110.3 2.353e+12 452.4 1.335e+12 62.26 1.895 5.201e+9 1.829e+12 363.7 111.8 2.398e+12 453.5 1.375e+12 62.80 1.972 5.289e+9 1.822e+12 369.3 113.3 2.444e+12 454.4 1.417e+12 63.34 2.052 5.378e+9 1.814e+12 374.8 114.8 2.489e+12 455.2 1.460e+12 63.88 2.136 5.468e+9 1.807e+12 380.4 116.3 2.534e+12 455.9 1.503e+12 64.42 2.224 5.558e+9 1.799e+12 386.1 117.8 2.580e+12 456.7 1.548e+12 64.98 2.316 5.650e+9 1.791e+12 391.7 119.3 2.626e+12 457.2 1.593e+12 65.52 2.411 5.743e+9 1.782e+12 397.4 120.8 2.666e+12 456.7 1.640e+12 65.99 2.510 5.837e+9 1.773e+12 403.2 122.3 2.696e+12 454.5 1.687e+12 66.31 2.613 5.932e+9 1.764e+12 409.0 123.7 2.729e+12 452.9 1.734e+12 66.69 2.721 6.027e+9 1.754e+12 414.8 125.2 2.763e+12 451.3 1.782e+12 67.08 2.832 6.122e+9 1.745e+12 420.7 126.7 2.796e+12 449.7 1.831e+12 67.47 2.948 6.217e+9 1.734e+12 426.5 128.1 2.828e+12 448.0 1.880e+12 67.86 3.069 6.312e+9 1.724e+12 432.5 wdata1columnnames ®consumer goods per person (per year) food food per person industrial output life expectancy persistent pollution index population resources (nonrenewable) services per personwdata2data E15.000e+9 6.051e+8 5.333 1.000 4000 9.000e+8 1.500 1.500 1.000 41.56 2.000 2.000 2.000 14.00 14.00 14.00 901.3 1000 20.00 20.00 20.00 37.00 5.920e+7 1.000 17.87 2.860e+10 0.4065 6.210e+9 32.27 5.163e+7 2.495e+7 1.256e+7 7.407e+6 6.707e+6 41.56 0.1681 3.187 3.800 2.000 1.200 4.800e+9 4.518 271.9 7.200 0.0000 0.7000 1.418 0.5822 0.1229 4000 0.7746 0.7746 0.1229 4.309e+11 269.3 1.171 2.000 0.1429 0.04000 0.001000 0.05000 0.05000 0.05000 0.1090 0.1090 0.1090 0.4300 0.4300 0.4300 0.4300 0.3104 0.3525 0.1086 0.1086 0.1086 0.1600 0.02000 1.000 0.001366 20.00 7.200 3.000 282.0 282.0 282.0 94.03 94.03 94.03 2.100e+11 1.500e+10 2.344e+10 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 6.650e+10 7.900e+11 41.56 400.0 600.0 8.919e+8 0.7500 0.0003700 0.0009667 6.675e+8 0.7500 1.336 2.000 1.000 3.809e+6 9.985e+5 600.0 1.103 0.001838 0.0000 8.000 0.2813 0.7000 0.9013 0.9013 0.9013 4000 7.975e+4 760.0 1.000 1.000 1.000 1.267 1.000 1.000 1.000 1.000 0.0000 0.0000 29.11 28.00 0.9350 1.074 1.036 1.036 1.180 0.9998 20.00 0.06900 82.80 39.93 4.167e+7 2.291e+7 9.130e+6 6.986 12.00 0.03839 0.01795 0.03898 0.1118 0.5463 0.1766 1.000 0.08549 29.11 1.045e+7 1.190e+7 4.800e+6 5.652e+6 1.000 1.000 1.000 1.045e+7 1.360e+8 0.1838 1.000 0.0000 0.0000 20.00 1995 2.500e+7 8.500e-5 1.600e+9 6.500e+8 7.000e+8 1.900e+8 6.000e+7 4000 3.200e+9 6.750e+8 7.770e+7 1.392e+8 2.300e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 2.826e+8 1.000 1.000 1.000 2.000e+12 0.004250 1.440e+11 7.200e+9 7.220e+9 1.000 1.000 1.000 1.440e+11 90.00 20.00 0.07000 1.198 230.0 20.00 7.246e+9 5.075 8.200e+6 10.00 0.005623 8.998e+6 4000 8.117e+9 2.874e+8 8.267 1.000 4000 9.359e+8 1.500 1.500 1.000 50.87 2.000 2.000 2.000 14.00 14.00 14.00 851.6 1000 20.00 20.00 20.00 40.86 7.112e+7 1.000 23.53 4.095e+10 0.3769 8.692e+9 32.02 5.573e+7 2.444e+7 1.294e+7 9.046e+6 9.316e+6 42.23 -0.006656 3.700 3.800 2.000 1.200 4.800e+9 5.241 294.0 7.234 0.07553 0.8133 1.417 0.5976 0.08780 4000 0.7735 0.7735 0.1176 4.956e+11 284.8 1.238 2.000 0.1636 0.04682 0.001000 0.05000 0.05000 0.05000 0.1091 0.1091 0.1091 0.4300 0.4300 0.4300 0.4300 0.3137 0.3325 0.1284 0.1284 0.1284 0.1740 0.02000 0.9983 0.0009207 20.00 7.628 3.000 298.4 298.4 298.4 111.1 111.1 111.1 3.007e+11 2.148e+10 3.166e+10 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 9.523e+10 7.900e+11 54.72 400.0 600.0 6.818e+8 0.4433 0.0003640 0.0009488 7.444e+8 0.7500 0.9159 2.000 0.9292 5.781e+6 1.099e+6 594.8 0.9746 0.001639 0.7861 6.635 0.2925 0.7000 0.8516 0.8516 0.8516 4000 1.033e+5 840.6 1.000 1.000 1.000 1.413 1.000 1.000 1.000 1.000 0.0000 0.0000 29.88 28.00 0.9344 1.102 1.036 1.036 1.181 0.9998 20.00 0.06570 78.15 40.84 4.259e+7 2.462e+7 1.160e+7 7.172 12.00 0.03684 0.01721 0.03752 0.1102 0.3683 0.2325 1.227 0.005375 29.17 1.075e+7 1.061e+7 7.737e+6 8.094e+6 1.000 1.000 1.000 1.583e+7 1.360e+8 0.1639 1.000 0.0000 0.0000 20.00 1995 2.228e+7 8.500e-5 1.740e+9 6.633e+8 7.515e+8 2.411e+8 8.451e+7 4000 3.200e+9 4.149e+8 1.095e+8 1.575e+8 2.253e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 4.047e+8 1.000 1.000 1.000 1.997e+12 0.004250 1.660e+11 8.298e+9 1.223e+10 1.000 1.000 1.000 1.660e+11 95.35 20.00 0.07000 1.197 230.0 20.00 1.039e+10 5.678 9.098e+6 10.00 0.005821 1.013e+7 4000 1.162e+10 4.163e+8 11.25 1.000 4000 9.823e+8 1.500 1.500 1.000 65.27 2.000 2.000 2.000 14.00 14.00 14.00 798.0 1000 20.00 20.00 20.00 40.19 7.624e+7 1.000 30.20 5.728e+10 0.3420 1.246e+10 31.61 5.997e+7 2.523e+7 1.335e+7 9.995e+6 1.140e+7 47.29 -0.005888 3.683 3.800 2.000 1.200 4.800e+9 5.195 365.2 7.670 0.07597 0.8140 1.410 0.6087 0.1155 4000 0.7708 0.7708 0.1038 5.741e+11 302.6 1.316 2.000 0.1461 0.04895 0.001000 0.05000 0.05000 0.05000 0.1095 0.1095 0.1095 0.4300 0.4300 0.4300 0.4300 0.3176 0.3337 0.1268 0.1268 0.1268 0.1897 0.02000 0.9959 0.001015 20.00 9.095 3.000 317.8 317.8 317.8 131.3 131.3 131.3 4.206e+11 3.005e+10 4.445e+10 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 1.332e+11 7.900e+11 70.22 400.0 600.0 6.984e+8 0.3686 0.0003444 0.0008877 8.110e+8 0.7500 0.8612 2.000 0.8729 5.836e+6 1.231e+6 593.6 1.122 0.001890 1.031 6.210 0.3070 0.7000 0.7980 0.7980 0.7980 4000 1.251e+5 927.6 1.000 1.000 1.000 1.563 1.000 1.000 1.000 1.000 0.0000 0.0000 30.87 28.00 0.9351 1.136 1.038 1.038 1.192 0.9998 20.00 0.06234 74.01 36.28 4.567e+7 2.641e+7 1.329e+7 7.305 12.00 0.03552 0.01657 0.03624 0.1083 0.4062 0.2985 1.298 0.008734 29.48 1.283e+7 1.224e+7 1.106e+7 1.132e+7 1.000 1.000 1.000 2.238e+7 1.360e+8 0.1890 1.000 0.0000 0.0000 20.00 1995 2.571e+7 8.500e-5 1.897e+9 7.102e+8 8.056e+8 2.758e+8 1.053e+8 4000 3.200e+9 3.621e+8 1.449e+8 1.914e+8 2.194e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 5.661e+8 1.000 1.000 1.000 1.992e+12 0.004250 2.157e+11 1.078e+10 1.689e+10 1.000 1.000 1.000 2.157e+11 113.7 20.00 0.07000 1.191 230.0 20.00 1.459e+10 5.679 1.023e+7 10.00 0.006053 1.148e+7 4000 1.652e+10 5.818e+8 15.22 1.000 4000 1.029e+9 1.500 1.500 1.000 84.20 2.000 2.000 2.000 14.00 14.00 14.00 726.5 1000 20.00 20.00 20.00 39.64 8.209e+7 1.000 39.02 8.079e+10 0.2958 1.768e+10 30.49 6.313e+7 2.592e+7 1.364e+7 1.057e+7 1.300e+7 57.75 -0.0008582 3.654 3.800 2.000 1.200 4.800e+9 5.112 451.0 8.640 0.07763 0.8164 1.399 0.6236 0.1617 4000 0.7711 0.7711 0.1055 6.763e+11 326.6 1.420 2.000 0.1428 0.05192 0.001000 0.05000 0.05000 0.05000 0.1098 0.1098 0.1098 0.4300 0.4300 0.4300 0.4300 0.3227 0.3367 0.1235 0.1235 0.1235 0.2071 0.02000 0.9926 0.001160 20.00 11.15 3.000 343.4 343.4 343.4 158.0 158.0 158.0 5.934e+11 4.238e+10 6.327e+10 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 1.879e+11 7.900e+11 90.74 400.0 600.0 7.196e+8 0.2908 0.0003184 0.0008020 8.834e+8 0.7500 0.8146 2.000 0.8163 6.531e+6 1.416e+6 592.5 1.474 0.002488 1.336 5.616 0.3215 0.7000 0.7265 0.7265 0.7265 4000 1.556e+5 1044 1.000 1.000 1.000 1.761 1.000 1.000 1.000 1.000 0.0000 0.0000 32.36 28.00 0.9387 1.181 1.043 1.043 1.216 0.9998 20.00 0.05787 68.58 33.05 4.957e+7 2.858e+7 1.481e+7 7.484 12.00 0.03369 0.01566 0.03444 0.1053 0.4640 0.3856 1.397 0.01132 30.11 1.717e+7 1.611e+7 1.566e+7 1.597e+7 1.000 1.000 1.000 3.163e+7 1.360e+8 0.2488 1.000 0.0000 0.0000 20.00 1995 3.383e+7 8.500e-5 2.071e+9 7.694e+8 8.711e+8 3.068e+8 1.235e+8 4000 3.200e+9 2.992e+8 1.889e+8 2.315e+8 2.133e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 7.986e+8 1.000 1.000 1.000 1.985e+12 0.004250 2.887e+11 1.443e+10 2.321e+10 1.000 1.000 1.000 2.887e+11 139.4 20.00 0.07000 1.178 230.0 20.00 2.063e+10 5.655 1.162e+7 10.00 0.006361 1.317e+7 4000 2.340e+10 8.134e+8 20.39 1.000 4000 1.083e+9 1.500 1.500 1.000 108.8 2.000 2.000 2.000 14.00 14.00 14.00 634.0 1000 20.00 20.00 20.00 39.01 8.899e+7 1.000 50.39 1.149e+11 0.2363 2.503e+10 28.63 6.532e+7 2.626e+7 1.373e+7 1.091e+7 1.443e+7 73.29 -0.001503 3.589 3.800 2.000 1.200 4.800e+9 4.982 552.0 10.16 0.07683 0.8152 1.388 0.6444 0.2380 4000 0.7759 0.7759 0.1294 8.146e+11 357.1 1.553 2.000 0.1512 0.05573 0.001000 0.05000 0.05000 0.05000 0.1103 0.1103 0.1103 0.4300 0.4300 0.4300 0.4300 0.3293 0.3390 0.1207 0.1207 0.1207 0.2281 0.02000 0.9878 0.001380 20.00 13.80 3.000 376.5 376.5 376.5 192.3 192.3 192.3 8.442e+11 6.030e+10 9.062e+10 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 2.673e+11 7.900e+11 117.2 400.0 600.0 7.857e+8 0.2520 0.0002849 0.0006919 9.715e+8 0.7500 0.8088 2.000 0.8118 8.077e+6 1.709e+6 590.9 2.040 0.003452 1.869 4.855 0.3386 0.7000 0.6340 0.6340 0.6340 4000 2.033e+5 1193 1.000 1.000 1.000 2.020 1.000 1.000 1.000 1.000 0.0000 0.0000 34.44 28.00 0.9461 1.238 1.051 1.051 1.254 0.9997 20.00 0.05206 61.52 30.89 5.446e+7 3.133e+7 1.654e+7 7.733 12.00 0.03114 0.01439 0.03193 0.1011 0.5520 0.4980 1.524 0.01420 31.16 2.396e+7 2.235e+7 2.209e+7 2.272e+7 1.000 1.000 1.000 4.482e+7 1.360e+8 0.3452 1.000 0.0000 0.0000 20.00 1995 4.694e+7 8.500e-5 2.281e+9 8.431e+8 9.537e+8 3.416e+8 1.427e+8 4000 3.200e+9 2.731e+8 2.405e+8 2.722e+8 2.061e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 1.136e+9 1.000 1.000 1.000 1.976e+12 0.004250 3.934e+11 1.967e+10 3.226e+10 1.000 1.000 1.000 3.934e+11 172.4 20.00 0.07000 1.158 230.0 20.00 2.948e+10 5.599 1.338e+7 10.00 0.006758 1.542e+7 4000 3.342e+10 1.159e+9 27.17 1.000 4000 1.158e+9 1.500 1.500 1.000 133.4 2.000 2.000 2.000 14.00 14.00 14.00 545.1 1000 20.00 20.00 20.00 37.30 1.006e+8 1.000 60.52 1.632e+11 0.1833 3.573e+10 20.37 5.494e+7 2.058e+7 1.017e+7 8.975e+6 1.521e+7 93.82 -0.002678 3.366 3.800 2.000 1.200 4.800e+9 4.584 687.3 12.07 0.05467 0.7820 1.362 0.7203 0.4468 4000 0.7884 0.7884 0.1918 1.013e+12 375.6 1.633 2.000 0.1809 0.05846 0.001000 0.05000 0.05000 0.05000 0.1149 0.1149 0.1149 0.4300 0.4300 0.4300 0.4300 0.3352 0.3361 0.1190 0.1190 0.1190 0.2697 0.02000 0.9811 0.002214 20.00 16.14 3.000 405.9 405.9 405.9 223.0 223.0 223.0 1.199e+12 8.563e+10 1.276e+11 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 3.796e+11 7.900e+11 140.7 400.0 600.0 8.623e+8 0.2000 0.0002551 0.0005971 1.139e+9 0.7500 0.7572 2.000 0.7625 1.148e+7 2.124e+6 588.8 2.864 0.004865 2.603 4.308 0.3619 0.7000 0.5451 0.5451 0.5451 4000 3.197e+5 1389 1.000 1.000 1.000 2.358 1.000 1.000 1.000 1.000 0.0000 0.0000 44.06 28.00 0.9506 1.272 1.302 1.060 1.302 0.9995 20.00 0.04444 52.33 28.86 6.482e+7 3.662e+7 2.003e+7 8.644 12.00 0.02073 0.009172 0.02191 0.08188 0.8857 0.5981 1.615 0.008885 33.82 3.382e+7 3.150e+7 3.146e+7 3.227e+7 1.000 1.000 1.000 6.373e+7 1.360e+8 0.4865 1.000 0.0000 0.0000 20.00 1995 6.616e+7 8.500e-5 2.697e+9 9.930e+8 1.109e+9 4.096e+8 1.858e+8 4000 3.200e+9 2.316e+8 3.058e+8 3.249e+8 1.965e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 1.613e+9 1.000 1.000 1.000 1.962e+12 0.004250 5.442e+11 2.721e+10 4.518e+10 1.000 1.000 1.000 5.442e+11 201.8 20.00 0.07000 1.133 230.0 20.00 4.363e+10 5.443 1.598e+7 10.00 0.007111 1.918e+7 4000 4.713e+10 1.593e+9 35.18 1.000 4000 1.257e+9 1.500 1.500 1.000 159.3 2.000 2.000 2.000 14.00 14.00 14.00 442.6 1000 20.00 20.00 20.00 35.14 1.124e+8 1.000 72.08 2.306e+11 0.1228 5.032e+10 17.68 5.655e+7 1.984e+7 9.659e+6 9.249e+6 1.780e+7 117.0 -0.0001659 3.264 3.800 2.000 1.200 4.800e+9 4.285 943.4 14.24 0.05214 0.7782 1.313 0.7403 0.6333 4000 0.8120 0.8120 0.3102 1.280e+12 400.3 1.740 2.000 0.2039 0.06154 0.001000 0.05000 0.05000 0.05000 0.1179 0.1179 0.1179 0.4300 0.4300 0.4300 0.4300 0.3419 0.3352 0.1170 0.1170 0.1170 0.3199 0.02000 0.9715 0.002683 20.00 18.89 3.000 439.5 439.5 439.5 257.9 257.9 257.9 1.693e+12 1.209e+11 1.797e+11 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 5.362e+11 7.900e+11 167.6 400.0 600.0 1.033e+9 0.2000 0.0002210 0.0005399 1.354e+9 0.7500 0.7633 2.000 0.7636 1.366e+7 2.840e+6 585.9 4.039 0.006893 3.679 3.846 0.3929 0.7000 0.4426 0.4426 0.4426 4000 4.332e+5 1616 1.000 1.000 1.000 2.759 1.000 1.000 1.000 1.000 0.0000 0.0000 48.06 28.00 0.9607 1.318 1.356 1.071 1.356 0.9993 20.00 0.03542 41.50 24.48 7.552e+7 4.334e+7 2.430e+7 8.883 12.00 0.01721 0.007375 0.01867 0.07389 1.073 0.7125 1.718 0.01113 38.71 4.794e+7 4.464e+7 4.423e+7 4.558e+7 1.000 1.000 1.000 8.981e+7 1.360e+8 0.6893 1.000 0.0000 0.0000 20.00 1995 9.375e+7 8.500e-5 3.199e+9 1.153e+9 1.310e+9 4.953e+8 2.410e+8 4000 3.200e+9 2.514e+8 3.742e+8 4.077e+8 1.837e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 2.279e+9 1.000 1.000 1.000 1.943e+12 0.004250 7.551e+11 3.775e+10 6.271e+10 1.000 1.000 1.000 7.551e+11 236.1 20.00 0.07000 1.104 230.0 20.00 6.321e+10 5.149 1.970e+7 10.00 0.007515 2.404e+7 4000 6.656e+10 2.489e+9 45.45 1.000 4000 1.370e+9 1.500 1.500 1.000 188.4 2.000 2.000 2.000 14.00 14.00 14.00 338.8 1000 20.00 20.00 20.00 32.64 1.244e+8 1.000 84.96 3.239e+11 0.05543 7.154e+10 15.09 5.754e+7 1.786e+7 9.005e+6 9.434e+6 2.123e+7 142.0 -0.002851 3.151 3.800 2.000 1.200 4.800e+9 3.986 1299 16.84 0.04878 0.7732 1.265 0.7615 0.8875 4000 0.8432 0.8432 0.4659 1.609e+12 422.0 1.835 2.000 0.2282 0.06448 0.001000 0.05000 0.05000 0.05000 0.1231 0.1231 0.1231 0.4300 0.4300 0.4300 0.4300 0.3494 0.3320 0.1150 0.1150 0.1150 0.3812 0.02000 0.9581 0.003231 20.00 22.96 3.000 477.0 477.0 477.0 296.9 296.9 296.9 2.379e+12 1.699e+11 2.501e+11 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 7.532e+11 7.900e+11 197.6 400.0 600.0 1.207e+9 0.2000 0.0001831 0.0004755 1.622e+9 0.7500 0.7443 2.000 0.7500 1.628e+7 4.044e+6 581.6 5.671 0.009751 5.176 3.552 0.4282 0.7000 0.3388 0.3388 0.3526 4000 5.692e+5 1864 1.000 1.000 1.000 3.204 1.000 1.000 1.000 1.000 0.0000 0.0000 52.87 28.00 0.9789 1.359 1.421 1.084 1.421 0.9990 20.00 0.02796 32.52 20.50 8.766e+7 5.161e+7 2.981e+7 9.138 12.00 0.01340 0.005782 0.01558 0.06713 1.292 0.8398 1.816 0.009452 43.50 6.775e+7 6.315e+7 6.227e+7 6.402e+7 1.000 1.000 1.000 1.263e+8 1.360e+8 0.9751 1.000 0.0000 0.0000 20.00 1995 1.326e+8 8.500e-5 3.812e+9 1.333e+9 1.557e+9 6.056e+8 3.163e+8 4000 3.200e+9 2.740e+8 4.354e+8 4.979e+8 1.686e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 3.201e+9 1.000 1.000 1.000 1.916e+12 0.004250 1.047e+12 5.235e+10 8.659e+10 1.000 1.000 1.000 1.047e+12 274.7 20.00 0.07000 1.073 230.0 20.00 9.269e+10 4.794 2.467e+7 10.00 0.007964 3.036e+7 4000 9.391e+10 3.055e+9 58.86 1.000 4000 1.488e+9 1.524 1.500 1.016 220.1 2.000 2.000 2.000 14.00 14.00 14.00 248.3 1000 20.00 20.00 20.00 30.18 1.369e+8 1.000 98.81 4.482e+11 0.02766 1.000e+11 12.79 5.799e+7 1.466e+7 8.263e+6 9.499e+6 2.557e+7 169.3 -0.001280 3.024 3.800 2.000 1.200 4.800e+9 3.683 1748 20.38 0.04417 0.7663 1.218 0.7825 1.245 4000 0.8668 0.8668 0.6682 2.002e+12 441.4 1.919 2.000 0.2464 0.06710 0.001000 0.05000 0.05000 0.05000 0.1273 0.1273 0.1273 0.4300 0.4300 0.4300 0.4300 0.3574 0.3260 0.1166 0.1166 0.1166 0.4268 0.02000 0.9380 0.003873 20.00 28.57 3.000 511.3 511.3 511.3 350.6 350.6 350.6 3.291e+12 2.351e+11 3.398e+11 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 1.042e+12 7.900e+11 229.8 400.0 600.0 1.431e+9 0.2000 0.0001681 0.0003976 1.943e+9 0.7500 0.7362 2.000 0.7388 1.870e+7 5.993e+6 575.9 8.019 0.01393 7.331 3.290 0.4651 0.7000 0.2483 0.2483 0.3209 4000 9.075e+5 2135 1.000 1.000 1.000 3.707 1.000 1.000 1.000 1.000 0.0000 0.0000 58.12 28.00 0.9882 1.395 1.508 1.106 1.508 0.9986 20.00 0.02293 26.41 17.45 1.011e+8 6.134e+7 3.664e+7 9.390 12.00 0.009573 0.004470 0.01280 0.06188 1.549 1.111 1.903 0.007850 48.17 9.589e+7 8.879e+7 8.761e+7 1.007e+8 1.000 1.000 1.000 1.884e+8 1.360e+8 1.393 1.000 0.0000 0.0000 20.00 1995 1.894e+8 9.666e-5 4.536e+9 1.532e+9 1.849e+9 7.423e+8 4.131e+8 4000 3.200e+9 2.977e+8 5.532e+8 5.797e+8 1.512e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 5.037e+9 1.000 1.000 1.000 1.876e+12 0.004833 1.458e+12 7.290e+10 1.216e+11 1.000 1.000 1.000 1.458e+12 321.4 20.00 0.07000 1.038 230.0 20.00 1.327e+11 4.443 3.194e+7 10.00 0.009042 4.101e+7 4000 1.267e+11 3.480e+9 73.28 1.000 4000 1.609e+9 1.563 1.500 1.042 253.2 2.000 2.000 2.000 14.00 14.00 14.00 158.3 1000 20.00 20.00 20.00 27.43 1.475e+8 1.000 113.3 6.093e+11 0.002388 1.336e+11 10.80 5.806e+7 1.088e+7 6.993e+6 9.656e+6 3.053e+7 199.1 -0.001066 2.894 3.800 2.000 1.200 4.800e+9 3.384 2336 24.93 0.04043 0.7607 1.169 0.8067 1.744 4000 0.8942 0.8942 0.9420 2.444e+12 454.4 1.975 2.000 0.2949 0.06900 0.001000 0.05000 0.05000 0.05000 0.1338 0.1338 0.1338 0.4300 0.4300 0.4300 0.4300 0.3659 0.3200 0.1162 0.1162 0.1162 0.4689 0.02000 0.9071 0.004652 20.00 34.98 3.000 546.7 546.7 546.7 407.9 407.9 407.9 4.475e+12 3.196e+11 4.534e+11 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 1.417e+12 7.900e+11 263.5 400.0 600.0 1.669e+9 0.2000 0.0001546 0.0003252 2.320e+9 0.7500 0.7194 2.000 0.7215 2.393e+7 1.017e+7 567.3 11.64 0.02052 10.55 3.100 0.5029 0.7000 0.1583 0.1583 0.2895 4000 1.239e+6 2410 1.000 1.000 1.000 4.248 1.000 1.000 1.000 1.000 0.0000 0.0000 63.34 28.00 0.9989 1.419 1.599 1.174 1.599 0.9979 20.00 0.01752 19.88 14.74 1.156e+8 7.262e+7 4.492e+7 9.680 12.00 0.006232 0.003199 0.01063 0.05666 1.861 1.405 1.967 0.004448 53.07 1.388e+8 1.275e+8 1.179e+8 1.512e+8 1.000 1.000 1.000 2.691e+8 1.360e+8 2.052 1.000 0.0000 0.0000 20.00 1995 2.791e+8 0.0001067 5.378e+9 1.745e+9 2.186e+9 9.081e+8 5.389e+8 4000 3.200e+9 3.219e+8 6.918e+8 6.555e+8 1.303e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 7.559e+9 1.000 1.000 1.000 1.814e+12 0.005334 2.016e+12 1.008e+11 1.647e+11 1.000 1.000 1.000 2.016e+12 374.8 20.00 0.07000 1.001 230.0 20.00 1.895e+11 4.050 4.259e+7 10.00 0.01022 5.497e+7 4000 1.755e+11 6.699e+9 94.21 1.000 4000 1.735e+9 1.624 1.500 1.083 287.7 2.000 2.000 2.000 14.00 14.00 14.00 127.2 1000 20.00 20.00 20.00 24.45 1.543e+8 1.000 128.1 8.086e+11 -0.02343 1.889e+11 9.326 5.887e+7 6.944e+6 5.417e+6 9.970e+6 3.654e+7 230.9 -0.003094 2.818 3.800 2.000 1.200 4.800e+9 3.152 3210 30.33 0.03549 0.7532 1.118 0.8293 2.503 4000 0.9320 0.9320 1.320 2.828e+12 448.0 1.948 2.000 0.3132 0.06884 0.001000 0.05000 0.05000 0.05000 0.1463 0.1463 0.1463 0.4300 0.4300 0.4300 0.4300 0.3745 0.3092 0.1146 0.1146 0.1146 0.5125 0.02000 0.8620 0.005787 20.00 41.89 3.000 582.8 582.8 582.8 466.4 466.4 466.4 5.938e+12 4.242e+11 5.814e+11 1.000 1.000 3.000 3.000 3.000 3.000 4000 0.1000 10.00 1.880e+12 7.900e+11 297.9 400.0 600.0 1.914e+9 0.2000 0.0001408 0.0002675 2.748e+9 0.7500 0.6965 2.000 0.7026 2.683e+7 1.364e+7 553.1 16.97 0.03069 15.04 3.116 0.5421 0.7000 0.1272 0.1272 0.2806 4000 1.559e+6 2587 1.000 1.000 1.000 4.678 1.000 1.000 1.000 1.000 0.0000 0.0000 67.86 28.00 1.012 1.408 1.707 1.255 1.707 0.9969 20.00 0.01358 15.02 11.51 1.294e+8 8.522e+7 5.459e+7 9.951 12.00 0.003564 0.002114 0.009050 0.05214 2.157 1.707 1.961 -0.006860 58.16 2.004e+8 1.835e+8 1.634e+8 2.155e+8 1.000 1.000 1.000 3.789e+8 1.360e+8 3.069 1.000 0.0000 0.0000 20.00 1995 4.173e+8 0.0001146 6.312e+9 1.948e+9 2.562e+9 1.102e+9 7.007e+8 4000 3.200e+9 3.470e+8 8.363e+8 7.303e+8 1.044e+9 0.1000 30.00 0.0000 1.000 0.0000 4000 1.077e+10 1.000 1.000 1.000 1.724e+12 0.005729 2.730e+12 1.365e+11 2.154e+11 1.000 1.000 1.000 2.730e+12 432.5 20.00 0.07000 0.9846 230.0 20.00 2.750e+11 3.614 5.654e+7 10.00 0.01143 7.213e+7 4000wdata2columnnames agricultural inputs agricultural inputs change agricultural inputs per hectare agricultural material toxicity index air pollution policy implementation time arable land assimilation half life assimilation half life in 1970 assimilation half life multiplier average industrial output per person [time avg.] average life of agricultural inputs average life of agricultural inputs 1 average life of agricultural inputs 2 average life of industrial capital average life of industrial capital 1 average life of industrial capital 2 average life of land average life of land normal average life of service capital average life of service capital 1 average life of service capital 2 birth rate (crude) births capacity utilization fraction consumer goods per person (per year) consumption (consumer goods per year) crowding multiplier from industry current agricultural inputs death rate (crude) deaths deaths ages 0 to 14 deaths ages 15 to 44 deaths ages 45 to 64 deaths ages 65 and up delayed industrial output per capita delayed labor utilization fraction change desired completed family size desired completed family size normal desired food ratio desired persistent pollution index desired resource usage rate desired total fertility development cost per hectare effective health services per capita family income expectation family response to social norm family size mult. from perc. lifetime fecundity multiplier fertility control allocation per capita fertility control effect time fertility control effectiveness [lower better] fertility control effectiveness table fertility control facilities per capita food food per person food ratio food shortage perception delay fraction of agr. inputs alloc. to land development fraction of agr. inputs for land maintenance fraction of agr. inputs from persistent materials fraction of ind. capital alloc. to obt. resources fraction of ind. capital alloc. to obt. resources 1 fraction of ind. capital alloc. to obt. resources 2 fraction of ind. output alloc. to agriculture fraction of ind. output alloc. to agriculture 1 fraction of ind. output alloc. to agriculture 2 fraction of ind. output alloc. to cons. fraction of ind. output alloc. to cons. const. fraction of ind. output alloc. to cons. const. 1 fraction of ind. output alloc. to cons. const. 2 fraction of ind. output alloc. to cons. var. fraction of ind. output alloc. to ind. investment fraction of ind. output alloc. to services fraction of ind. output alloc. to services 1 fraction of ind. output alloc. to services 2 fraction of population urban fraction of resources from persistent materials fraction of resources remaining fraction of services allocated to fertility control health services impact delay health services per person income expectation averaging time indicated food per person indicated food per person 1 indicated food per person 2 indicated service output per person indicated service output per person 1 indicated service output per person 2 industrial capital industrial capital depreciation industrial capital investment industrial capital out. ratio mult. f. l. y. tech. industrial capital out. ratio mult. f. poll. tech. industrial capital out. ratio mult. f. r. c. tech. industrial capital output ratio industrial capital output ratio 1 industrial capital output ratio 2 industrial equilibrium time industrial material emissions factor industrial material toxicity index industrial output industrial output in 1970 industrial output per person industrial output per person desired inherent land fertility jobs jobs per hectare jobs per industrial capital unit jobs per service capital unit labor force labor force participation fraction labor utilization fraction labor utilization fraction delay time labor utilization fraction delayed land development rate land erosion rate land fertility land fertility degradation land fertility degradation rate land fertility regeneration land fertility regeneration time land fraction cultivated land fraction harvested land life multiplier from yield land life multiplier from yield 1 land life multiplier from yield 2 land life policy implementation time land removal for urban-industrial use land yield land yield multiplier from air pollution land yield multiplier from air pollution 1 land yield multiplier from air pollution 2 land yield multiplier from capital land yield multiplier from technology land yield multiplier from technology 1 land yield multiplier from technology 2 land yield technology land yield technology change rate land yield technology change rate mult. life expectancy life expectancy normal lifetime multiplier from crowding lifetime multiplier from food lifetime multiplier from health services lifetime multiplier from health services t. < 1940 lifetime multiplier from health services t. > 1940 lifetime multiplier from persistent pollution lifetime perception delay marginal land yield multiplier from capital marginal productivity of agricultural inputs marginal productivity of land development maturation age 14 to 15 maturation age 44 to 45 maturation age 64 to 65 maximum total fertility maximum total fertility normal mortality ages 0 to 14 mortality ages 15 to 44 mortality ages 45 to 64 mortality ages 65 and up need for fertility control per capita resource use multiplier perceived food ratio perceived food ratio change perceived life expectancy persistent pollution appearance rate persistent pollution assimilation rate persistent pollution generation by agriculture persistent pollution generation by industry persistent pollution generation factor persistent pollution generation factor 1 persistent pollution generation factor 2 persistent pollution generation rate persistent pollution in 1970 persistent pollution index persistent pollution technology [lower better] persistent pollution technology change persistent pollution technology change mult. persistent pollution transmission delay policy implementation time pollution (persistent) pollution per unit of ind. output population population ages 0 to 14 population ages 15 to 44 population ages 45 to 64 population ages 65 and up population equilibrium switch time potential arable land total potential jobs in agricultural sector potential jobs in industrial sector potential jobs in service sector potentially arable land processing loss reproductive lifetime resource conservation tech. change mult. resource conservation technology [lower better] resource conservation technology change resource extraction technology time resource usage rate resource use factor resource use factor 1 resource use factor 2 resources (nonrenewable) resources used per unit of ind. output service capital service capital depreciation service capital investment service capital output ratio service capital output ratio 1 service capital output ratio 2 service output services per person social adjustment delay social discount social family size norm subsistence food per person technology development delay total agricultural investment total fertility urban-industrial land urban-industrial land development time urban-industrial land per person urban-industrial land required zero population growth timewdata1rownames '1900.0 1901.0 1902.0 1903.0 1904.0 1905.0 1906.0 1907.0 1908.0 1909.0 1910.0 1911.0 1912.0 1913.0 1914.0 1915.0 1916.0 1917.0 1918.0 1919.0 1920.0 1921.0 1922.0 1923.0 1924.0 1925.0 1926.0 1927.0 1928.0 1929.0 1930.0 1931.0 1932.0 1933.0 1934.0 1935.0 1936.0 1937.0 1938.0 1939.0 1940.0 1941.0 1942.0 1943.0 1944.0 1945.0 1946.0 1947.0 1948.0 1949.0 1950.0 1951.0 1952.0 1953.0 1954.0 1955.0 1956.0 1957.0 1958.0 1959.0 1960.0 1961.0 1962.0 1963.0 1964.0 1965.0 1966.0 1967.0 1968.0 1969.0 1970.0 1971.0 1972.0 1973.0 1974.0 1975.0 1976.0 1977.0 1978.0 1979.0 1980.0 1981.0 1982.0 1983.0 1984.0 1985.0 1986.0 1987.0 1988.0 1989.0 1990.0 1991.0 1992.0 1993.0 1994.0 1995.0 1996.0 1997.0 1998.0 1999.0 2000.0 wdata2rownames W1900.0 1910.0 1920.0 1930.0 1940.0 1950.0 1960.0 1970.0 1980.0 1990.0 2000.0 'Graph and Table Objects for Revolution U helvetica W helvetica U helvetica U helvetica U helvetica W helvetica U helvetica U times W Times U Times U helvetica U helvetica U Arial U Arial U Arial U Courier U Lucida Grande U Lucida Grande U Lucida Grande U Times W Verdana U Verdana U Arial U Lucida Grande U times U helvetica cREVGeneral bookmarks debugObjects handlerList preOpenStack openCardprevHandler openCardtempScript script cREVGeometryCache stackID 16507 ź graph object PGon graphClicked n, x, y put "You clicked on curve "& n &" at x = "& x &", y = "& y &"." end graphClicked on graphEdited put the graphYDataEdited of group "graph" into tNewYValue put "You set the volume to "& tNewYValue &"." end graphEdited # The following functions were used during testing of the graph object. function firstItemOnly pS put "" into tR put 0 into i repeat for each item tItem in pS add 1 to i if i=1 then put tItem &"," after tR else put "," after tR end repeat if not (char -1 of pS = ",") then delete char -1 of tR return tR end firstItemOnly function selectedItemsOnly pS, pSelectionList put "" into tR put 0 into i repeat for each item tItem in pS add 1 to i if i is among the items of pSelectionList then put tItem &"," after tR else put "," after tR end repeat if not (char -1 of pS = ",") then delete char -1 of tR return tR end selectedItemsOnly # Return whether a line of comma-separated numbers are ordered (nondecreasing or # nonincreasing). function dataOrdered s put true into tNondecreasing # Assume true until proven false. put true into tNonincreasing # Assume true until proven false. put (item 1 of s) + 0 into tPrevX repeat for each item tXStr in s put tXStr + 0 into tX if tX < tPrevX then put false into tNondecreasing if tX > tPrevX then put false into tNonincreasing if not (tNondecreasing or tNonincreasing) then exit repeat end repeat return (tNondecreasing or tNonincreasing) end dataOrdered function flipOrder s put "" into r put the number of items in s into n repeat with i = n down to 1 put (item i of s) &"," after r end repeat delete char -1 of r return r end flipOrder on flipIt put "10.1,11,10.9,11.4,11.7,12,11.5,11,10,10.3,10,11.5,12,11.5,,11,10,8.5,7.5,10,7,8" into s put flipOrder(s) end flipIt Č cREVGeometryCacheIDs 1169586828424 160581166423936986 31121169586828425 160591166423936987 31401166423936988 37861169586828427 160621166423936989 37871166423936990 55041166423936991 114421169586828429 160631166423936992 118561169586855137 160551169586855138 160601169586855139 160611166423936974 62961166423936975 62951166423936976 10051166423936977 10041166423936981 10061166423936982 12161166423936983 26831169586828421 160561166423936984 26911169586828422 160571166423936985 3034 cREVGeometrycache order total 25 ķ ī Ą { Ś ( D Ź Ė ,² .P > table object Pon openCard # Examples 3 and 4 require data in a global variable. Set the global variable if necessary # (this is necessary if someone saved the stack with example 3 or 4 showing and just # started up the stack). global gData, zztbgetUnformattedDataFromGlobal if field "info" contains "Example 3:" then put the wdata1data of this stack into gData else if field "info" contains "Example 4:" then put the wdata2data of this stack into zztbgetUnformattedDataFromGlobal put tbGetColumns(183, the wdata2data of this stack) into gData end if pass openCard end openCard function tbGetColumns pNumColumns, pS set the itemDelimiter to tab put pNumColumns + 0 into tNumColumns put "" into r repeat for each line l in pS put item 1 to tNumColumns of l after r put cr after r end repeat return r delete the last char of r #Delete trailing return. end tbGetColumns on doubleClickOnTable pWhereClicked put "You clicked on the table, part (column, row): "& pWhereClicked end doubleClickOnTable Č cREVGeneral scriptChecksum >ūÖk Ź@§_§hæ bookmarks handlerList (openCard tbGetColumns doubleClickOnTabletempScript prevHandler doubleClickOnTablescriptSelection char 1016 to 1015script :
on openCard
# Examples 3 and 4 require data in a global variable. Set the global variable if necessary
# (this is necessary if someone saved the stack with example 3 or 4 showing and just
# started up the stack).
global gData, zztbgetUnformattedDataFromGlobal
if field "info" contains "Example 3:" then
put the wdata1data of this stack into gData
else if field "info" contains "Example 4:" then
put the wdata2data of this stack into zztbgetUnformattedDataFromGlobal
put tbGetColumns(183, the wdata2data of this stack) into gData
end if
pass openCard
end openCard
function tbGetColumns pNumColumns, pS
set the itemDelimiter to tab
put pNumColumns + 0 into tNumColumns
put "" into r
repeat for each line l in pS
put item 1 to tNumColumns of l after r
put cr after r
end repeat
return r
delete the last char of r #Delete trailing return.
end tbGetColumns
on doubleClickOnTable pWhereClicked
put "You clicked on the table, part (column, row): "& pWhereClicked
end doubleClickOnTable
cREVGeometryCacheIDs 1166424932901 62601166424932902 62651166424932903 62661166424932904 62751166424932905 68111166424932906 68121166424932896 62191166424932907 68241166424932897 62511166424932908 68141166424932898 62541166424932910 68161166424932909 68151166424932899 62551166424932911 68171166424932912 68181166424932913 68191166424932914 68201166424932915 68211166424932916 68221166424932917 68231166424932918 68251166423936974 62961166423936975 62951166424932900 6257 cREVGeometryCache order total 25 K k n o q t y z © ķ graph IĆ# Copyright (c) Kenneth L. Simons 2000-2003. # All Rights Reserved. # The author hereby allows others to use the graph object according to the following principles: # Anyone may use the graph object for any purpose. # Rights to use of the original object must remain in the public domain. local aNumScaleLabelsCreated local aXScaleTextBottom local aDuplicatedPointNums on makeGraph # 1. Ensure (some of the) properties are okay. ensurePropertiesOkay # 2. Get/Calculate subsidiary information. # 2a. Main graph coordinates. put the graphMainRect of me into tGMR set the rect of button "graph background" of me to tGMR put item 1 of tGMR into a # Left side coordinate of main graph. put item 4 of tGMR into b # Bottom coordinate of main graph. put (item 3 of tGMR) - a into w # Width of main graph. put b - (item 2 of tGMR) into h # Height of main graph. # 2b. Data and axis scales. put "" into aDuplicatedPointNums put the graphX of me into tXData put singleNonmissingItemNum(tXData) into tSingleNonmXItemN if tSingleNonmXItemN <> "" then put ","& (item tSingleNonmXItemN of tXData) after item tSingleNonmXItemN of tXData # If only one data point, make 2 identical DPs for correct graphing. noteDuplicatedPointNum tSingleNonmXItemN end if put the number of items in tXData into tNumXPoints if (char -1 of tXData) = "," then add 1 to tNumXPoints # Include the blank item at the end. put nonBlankItems(tXData) into tXDataNonBlank # Used when finding min and max. put min(tXDataNonBlank) into tXMin if (the graphXMin of me) <> "" then put min(the graphXMin of me,tXMin) into tXMin put max(tXDataNonBlank) into tXMax if (the graphXMax of me) <> "" then put max(the graphXMax of me,tXMax) into tXMax put (tXMin = "" or tXMin > 0) and (the graphXLog of me = true) into tXLogarithmic if tXLogarithmic then put listLn(tXData) into tXData if tXMin <> "" then put ln(tXMin) into tXMin if tXMax <> "" then put ln(tXMax) into tXMax end if if (the graphXRound of me) = "true" then put roundRange(tXMin, tXMax, tXLogarithmic) into tRoundedXRange put item 1 of tRoundedXRange into tXMin put item 2 of tRoundedXRange into tXMax end if if tXMin = tXMax then if tXMin = 0 then put -1 into tXMin put 1 into tXMax else if tXMin > 0 then put tXMin * 2 into tXMax put 0 into tXMin else put 0 into tXMax put tXMin * 2 into tXMin end if end if put (the number of lines in the graphY of me) into tNumCurves repeat with i = 1 to tNumCurves put line i of the graphY of me into tYData[i] # In general this is a line of multiple numbers (so don't use format). end repeat repeat with i = 1 to tNumCurves if tSingleNonmXItemN <> "" then if (the number of items in tYData[i]) >= tSingleNonmXItemN then # This if-then is not crucial, but better with very many data points. put ","& item tSingleNonmXItemN of tYData[i] after item tSingleNonmXItemN of tYData[i] # Duplicate a data point, because it has been duplicated (for correct graphing) in the x-data. end if end if put singleNonmissingItemNum(tYData[i]) into tSingleNonmYItemN if tSingleNonmYItemN <> "" then # If only one data point, make 2 identical DPs for correct graphing. put ","& (item tSingleNonmYItemN of tXData) after item tSingleNonmYItemN of tXData add 1 to tNumXPoints repeat with j = 1 to tNumCurves put ","& (item tSingleNonmYItemN of tYData[j]) after item tSingleNonmYItemN of tYData[j] end repeat noteDuplicatedPointNum tSingleNonmYItemN end if put nonBlankItems(tYData[i]) into thisYDataNonBlank # Used when finding min and max. put line i of the graphYMin of me into tThisGraphYMin put format("%14.12e", min(thisYDataNonBlank)) into tYMin[i] if tThisGraphYMin <> "" then put format("%14.12e", min(tThisGraphYMin,tYMin[i])) into tYMin[i] put line i of the graphYMax of me into tThisGraphYMax put format("%14.12e", max(thisYDataNonBlank)) into tYMax[i] if tThisGraphYMax <> "" then put format("%14.12e", max(tThisGraphYMax,tYMax[i])) into tYMax[i] end repeat repeat with i = 1 to tNumCurves put (tYMin[i] = "" or tYMin[i] > 0) and ((the graphYLog of me) = "true" or (line i of the graphYLog of me) = true) into tYLogarithmic[i] if tYLogarithmic[i] then put listLn(tYData[i]) into tYData[i] if tYMin[i] <> "" then put ln(tYMin[i]) into tYMin[i] if tYMax[i] <> "" then put ln(tYMax[i]) into tYMax[i] end if end repeat put the graphYScaleSame of me into tYScalesSame # Determine whether y-scales forced to be the same. if tYScalesSame = true then # Disallow y-scales same if some logarithmic, some not. repeat with i = 2 to tNumCurves if tYLogarithmic[i] <> tYLogarithmic[1] then put false into tYScalesSame exit repeat end if end repeat end if if tYScalesSame = "true" then # A single ymin and ymax scale for all curves. put tYMin[1] into tYMinAll put tYMax[1] into tYMaxAll repeat with i = 2 to tNumCurves put min(tYMinAll,tYMin[i]) into tYMinAll put max(tYMaxAll,tYMax[i]) into tYMaxAll end repeat if tYMinAll = tYMaxAll then if tYMinAll = 0 then put -1 into tYMinAll put 1 into tYMaxAll else if tYMinAll > 0 then put tYMinAll * 2 into tYMaxAll put 0 into tYMinAll else put 0 into tYMaxAll put tYMinAll * 2 into tYMinAll end if end if if (the graphYRound of me) = "true" then put roundRange(tYMinAll, tYMaxAll, tYLogarithmic[1]) into tRoundedYRange put item 1 of tRoundedYRange into tYMinAll put item 2 of tRoundedYRange into tYMaxAll end if put format("%14.12e", tYMinAll) into tYMinAll put format("%14.12e", tYMaxAll) into tYMaxAll repeat with i = 1 to tNumCurves put tYMinAll into tYMin[i] put tYMaxAll into tYMax[i] end repeat else # Different ymin and ymax scales for different curves. if (the graphYRound of me) = "true" then repeat with i = 1 to tNumCurves put roundRange(tYMin[i], tYMax[i], tYLogarithmic[i]) into tRoundedYRange put format("%14.12e", item 1 of tRoundedYRange) into tYMin[i] put format("%14.12e", item 2 of tRoundedYRange) into tYMax[i] end repeat else repeat with i = 1 to tNumCurves if tYMin[i] = tYMax[i] then if tYMin[i] = 0 then put -1 into tYMin[i] put 1 into tYMax[i] else if tYMin[i] > 0 then put tYMin[i] * 2 into tYMax[i] put 0 into tYMin[i] else put 0 into tYMax[i] put tYMin[i] * 2 into tYMin[i] end if end if end repeat end if end if # 2c. Whether the y-axis scales for multiple variables are the same. if tYScalesSame <> "true" then put true into tYScalesSame # Assume same until proven different. repeat with i = 2 to tNumCurves if tYMin[i] <> tYMin[1] or tYMax[i] <> tYMax[1] then put false into tYScalesSame exit repeat end if end repeat end if # 2d. Scaling factors for plotting data. put w / (tXMax - tXMin) into tXScaleFactor repeat with i = 1 to tNumCurves put format("%14.12e", h / (tYMax[i] - tYMin[i])) into tYScaleFactor[i] end repeat # 2f. X and Y values at which to plot tic marks. if the graphXTicks of me = "none" then put "" into tXTickLocs else if (word 1 of the graphXTicks of me) = "about" then put chooseTickLocs(tXMin, tXMax,(word 2 of the graphXTicks of me),"") into tXTickLocs else if (word 1 of the graphXTicks of me) = "exactly" or (word 1 of the graphXTicks of me) = "exact" then put chooseTickLocs(tXMin, tXMax,"",(word 2 of the graphXTicks of me)) into tXTickLocs else if the graphXTicks of me <> "" then put the graphXTicks of me into tXTickLocs else put tXMin &","& tXMax into tXTickLocs end if if the graphYTicks of me = "none" then put "" into tYTickLocs else if (word 1 of the graphYTicks of me) = "about" then put chooseTickLocs(tYMin[1], tYMax[1],(word 2 of the graphYTicks of me),"") into tYTickLocs else if (word 1 of the graphYTicks of me) = "exactly" or (word 1 of the graphYTicks of me) = "exact" then put chooseTickLocs(tYMin[1], tYMax[1],"",(word 2 of the graphYTicks of me)) into tYTickLocs else if the graphYTicks of me <> "" then put the graphYTicks of me into tYTickLocs else put tYMin[1] &","& tYMax[1] into tYTickLocs # Y tic locs are defined in terms of the first y variable only. end if # 3. Lock the screen before doing anything that affects the display. lock screen # 4. Delete existing graphics and fields in this graph object, and the "graph cover" button if any. put the number of graphics in me into nGraphics repeat with i = nGraphics down to 1 delete graphic i of me end repeat put the number of fields in me into nFields repeat with i = nFields down to 1 delete field i of me end repeat if there is a button "graph cover" of me then delete button "graph cover" of me # 5. Draw axes. reset templateGraphic set the style of the templateGraphic to "polygon" set the lineSize of the templateGraphic to the graphAxisWidth of me set the points of the templateGraphic to a &","& (b-h) & cr & a &","& b & cr & (a+w) &","& b createGraphic "axes" put a &","& (b-h) &","& (a+w) &","& b into tGraphCoverRect # May be used below, for editable graphs. # 6. Draw tick marks. # 6a. Draw major tick marks and labels. put "" into aXScaleTextBottom put 0 into aNumScaleLabelsCreated put "" into tTickPoints put tXTickLocs <> "" and (the graphXTicksVisible of me) <> "false" into tXTicksVisible put tXTickLocs <> "" and (the graphXScaleVisible of me) <> "false" into tXScaleVisible if tXTicksVisible or tXScaleVisible then if the graphXTicksInset of me = "true" or (not tXTicksVisible) then put the graphTickMajorWidth of me into tTickOffset else put 0 into tTickOffset end if repeat for each item thisXLoc in tXTickLocs put round(a + (thisXLoc - tXMin) * tXScaleFactor) into thisXWindowLoc put b + (the graphTickMajorWidth of me) - tTickOffset into tYAtBottomOfTick if tXTicksVisible then put thisXWindowLoc &","& (b-tTickOffset) & cr & thisXWindowLoc &","& tYAtBottomOfTick & cr & cr after tTickPoints if tXScaleVisible then if tXLogarithmic then put exp(thisXLoc) into thisXLoc makeAxisLabel "x", thisXWindowLoc, tYAtBottomOfTick, thisXLoc end if end repeat end if put tYTickLocs <> "" and (the graphYTicksVisible of me) <> "false" into tYTicksVisible put the graphYScaleVisible of me into tGYSVOM if tGYSVOM = "true" then if not tYScalesSame then # When the graphYScaleVisible is true and there are multiple curves with different scales, display scales for each. put "" into tGYSVOM repeat with i = 1 to tNumCurves put i &"," after tGYSVOM end repeat delete the last char of tGYSVOM #Delete trailing comma. end if end if put tYTickLocs <> "" and tGYSVOM <> "false" into tYScaleVisible if tYTicksVisible or tYScaleVisible then if the graphYTicksInset of me = "true" or (not tYTicksVisible) then put the graphTickMajorWidth of me into tTickOffset else put 0 into tTickOffset end if repeat for each item thisYLoc in tYTickLocs # Step through different tick marks. (Recall that tYTickLocs is defined only in terms of the first y-variable.) put round(b - (thisYLoc - tYMin[1]) * tYScaleFactor[1]) into thisYWindowLoc put a - the graphTickMajorWidth of me + tTickOffset into tXAtLeftOfTick if tXTicksVisible then put tXAtLeftOfTick &","& thisYWindowLoc & cr & (a + tTickOffset) &","& thisYWindowLoc & cr & cr after tTickPoints if tYScaleVisible then if tGYSVOM = "true" then if tYLogarithmic[1] then put exp(thisYLoc) into tYLocsForScaleLabel else put thisYLoc into tYLocsForScaleLabel put "" into tYColorsForScaleLabel else if thisYLoc = tYMax[1] then put 1 into tYFrac else put (thisYLoc - tYMin[1]) / (tYMax[1] - tYMin[1]) into tYFrac put "" into tYLocsForScaleLabel put "" into tYColorsForScaleLabel put the number of items in tGYSVOM into n repeat with i = 1 to n # Step through different curves. put item i of tGYSVOM into thisCurveNum put tYMin[thisCurveNum] into tThisMin put tYMax[thisCurveNum] - tThisMin into tThisDiff if tYFrac = 1 then put tYMax[thisCurveNum] into tThisY #Avoid rounding error. else put tThisMin + tThisDiff * tYFrac into tThisY if tYLogarithmic[i] then put exp(tThisY) into tThisY put tThisY & return after tYLocsForScaleLabel put line i of the graphLineColors of me into tGC if tGC = "" then put the effective foregroundColor of me into tGC put tGC & return after tYColorsForScaleLabel end repeat delete the last char of tYLocsForScaleLabel #Delete trailing return. delete the last char of tYColorsForScaleLabel #Delete trailing return. end if makeAxisLabel "y", tXAtLeftOfTick, thisYWindowLoc, tYLocsForScaleLabel, tYColorsForScaleLabel end if end repeat end if if tXTicksVisible or tYTicksVisible then reset templateGraphic set the style of the templateGraphic to "polygon" set the points of the templateGraphic to tTickPoints createGraphic "ticks" end if # 7. Draw data. repeat with i = 1 to tNumCurves put tYScaleFactor[i] into thisYScaleFactor reset templateGraphic set the style of the templateGraphic to "polygon" if (line i of the graphLinesVisible of me) = "false" then put 0 into tGLW else put line i of the graphLineWidths of me into tGLW if tGLW is an integer then set the lineSize of the templateGraphic to tGLW put "" into tPoints repeat with j = 1 to tNumXPoints put item j of tXData into x put item j of tYData[i] into y if x = "" or y = "" then put cr after tPoints else put round(a + (x - tXMin) * tXScaleFactor) &","& round(b - (y - tYMin[i]) * thisYScaleFactor) & cr after tPoints end repeat delete char -1 of tPoints # Delete trailing return. set the points of the templateGraphic to tPoints put line i of the graphLineColors of me into tGC if tGC <> "" then set the foregroundColor of the templateGraphic to tGC put line i of the graphLineDashes of me into tGD if tGD <> "" then set the dashes of the templateGraphic to tGD if the graphClickable of me = "true" then set the script of the templateGraphic to "on mouseUp"& cr &" graphClicked "& i &", ((item 1 of the clickLoc) - "& a &") / "& tXScaleFactor &" + "& tXMin &", ("& b &" - (item 2 of the clickLoc)) / "& thisYScaleFactor &" + "& tYMin[i] & cr &"end mouseUp" end if put graphMarkerLineToPoints(line i of the graphMarkers of me) into tGM if tGM <> "" then put line 1 of tGM into tGMFilled put line 2 to -1 of tGM into tGMPoints set the markerDrawn of the templateGraphic to true set the markerFilled of the templateGraphic to tGMFilled set the markerPoints of the templateGraphic to tGMPoints if tGC <> "" then set the markerColor of the templateGraphic to tGC set the markerFillColor of the templateGraphic to tGC end if end if createGraphic "curve "& i end repeat # 8. Title. put the graphTitle of me into tMainTitle if tMainTitle <> "" then put the graphTitleTextSize of me into tTS if tTS = "" then put 12 into tTS put tTS + 4 into tTH put round(((item 1 of tGMR)+(item 3 of tGMR))/2) into tXLoc put round((item 2 of tGMR) - (the graphTitleGap of me)) into tBottom makeAField "title", tMainTitle, "center", the graphTitleTextFont of me, the graphTitleTextStyle of me, "", tTS, tTH, (tXLoc &","& 0), "", "", "", tBottom end if # 9. Axis variable/label names. put the graphXYLabelTextSize of me into tTS if tTS = "" then put 9 into tTS put tTS + 4 into tTH put the graphXLabel of me into tGXL if tGXL <> "" then put round(((item 1 of tGMR)+(item 3 of tGMR))/2) + (the graphXLabelXNudge of me) into tXLoc if tXTicksVisible then put the graphTickMajorWidth of me into tYOffset else put 0 into tYOffset end if if aXScaleTextBottom <> "" then put aXScaleTextBottom - 1 into tTopOfField else put (item 4 of tGMR) + tYOffset - 1 into tTopOfField end if add the graphXLabelYNudge of me to tTopOfField makeAField "x varname", tGXL, "center", the graphXYLabelTextFont of me, "", "", tTS, tTH, (tXLoc &","& 0), "", tTopOfField, "", "" put the bottom of field "x varname" of me into tXLabelingBottom # Used when making a key. else # No x-axis label was created. if aXScaleTextBottom <> "" then put aXScaleTextBottom into tXLabelingBottom # Used when making a key. else put b into tXLabelingBottom # Used when making a key. end if end if put the graphYLabel of me into tGYL if tGYL <> "" then # The left and bottom chosen here are quite arbitrary; there are certainly better methods to choose them. put (item 1 of tGMR) - 30 into tLeft if tXTicksVisible then subtract the graphTickMajorWidth of me from tLeft end if add the graphYLabelXNudge of me to tLeft put (item 2 of tGMR) - 6 into tBottom add the graphYLabelYNudge of me to tBottom makeAField "y varname", tGYL, "left", the graphXYLabelTextFont of me, "", "", tTS, tTH, "", tLeft, "", "", tBottom end if # 10. Key. # 10a. Whether to create a key, and what its text will say. put the graphYVariableNames of me into tKeyNames put the graphYScalesInKey of me into tIncludeYScalesInKey put the graphKeyLogIndicator of me into tLogIndicator if tLogIndicator <> "" then put " " before tLogIndicator put false into tMakeKey # Assume false until proven true. put "" into tKeyContents put 0 into i repeat for each line tThisKeyName in tKeyNames add 1 to i if tThisKeyName <> "" then put true into tMakeKey put tThisKeyName after tKeyContents if tYLogarithmic[i] then put tLogIndicator after tKeyContents put line i of the graphYUnitsOfMeasureInKey of me into tUnitsOfMeasure if tIncludeYScalesInKey then if tUnitsOfMeasure <> "" then put " " before tUnitsOfMeasure put " ("& displayRange(tYMin[i], tYMax[i]) & tUnitsOfMeasure &")" after tKeyContents # State the range and units of measure for this variable. else if tUnitsOfMeasure <> "" then put " ("& tUnitsOfMeasure &")" after tKeyContents # State the units of measure for this variable. end if put return after tKeyContents end if if i >= tNumCurves then exit repeat end repeat delete char -1 of tKeyContents # Delete trailing return. # 10b. Make key. if tMakeKey then # 10b1. Make the text of the key. put the graphKeyTextSize of me into tTS put tTS + min(0, round(the graphKeyTextSeparation of me)) into tTH put a + 20 + (the graphKeyXNudge of me) into tLeft put tXLabelingBottom + 12 + (the graphKeyYNudge of me) into tTop makeAField "key", tKeyContents, "left", the graphKeyTextFont of me, "plain", "", tTS, tTH, "", tLeft, tTop, "", "" # 10b2. Plot line segments in the key. repeat with i = 1 to tNumCurves put "curve "& i into tCurveName put the points of graphic tCurveName of me into tPoints put tTop + roundUp(tTH/2) + (i-1)*tTH into tLabelLineY put (tLeft - 20) &","& tLabelLineY into tPointA put (tLeft - 5) &","& tLabelLineY into tPointB put cr & cr & tPointA & cr & tPointB after tPoints set the points of graphic tCurveName of me to tPoints end repeat end if # 11. If requested, prepare for editable graph. if (the graphEditable of me) and (tNumCurves > 0) then reset templateButton set the rect of the templateButton to tGraphCoverRect set the script of the templateButton to "on mouseDown"& cr &" graphCoverClicked"& cr &"end mouseDown" set the showName of the templateButton to false set the showBorder of the templateButton to false set the threeD of the templateButton to false set the opaque of the templateButton to false set the traversalOn of the templateButton to false set the autoHilite of the templateButton to false create button "graph cover" in me set the cpEditCurveNum of button "graph cover" of me to tNumCurves set the cpGraphYMin of button "graph cover" of me to tYMin[tNumCurves] set the cpGraphYMax of button "graph cover" of me to tYMax[tNumCurves] # A minor part of setting up is determining whether the x-data are ordered, because # if the x-data are nondecreasing or nonincreasing, processing can be sped up for # editing graphs. put the points of graphic ("curve "& tNumCurves) of me into tPointsOfCurve if tMakeKey then delete line -3 to -1 of tPointsOfCurve # Ignore parts that pertain to the key. set the cpXDataRanges of button "graph cover" of me to clickXRanges(getXVals(tPointsOfCurve)) set the graphYDataEdited of me to tYData[tNumCurves] else set the graphYDataEdited of me to "" end if # 12. Unlock the screen and go back to the browse (hand) tool. reset templateField reset templateGraphic reset templateButton choose browse tool unlock screen end makeGraph on noteDuplicatedPointNum pNewPointNum put the number of items in aDuplicatedPointNums into tN repeat with i = 1 to tN put item i of aDuplicatedPointNums into tPN if pNewPointNum < tPN then put (tPN+1) into item i of aDuplicatedPointNums end repeat put pNewPointNum into item (tN+1) of aDuplicatedPointNums sort items of aDuplicatedPointNums numeric descending end noteDuplicatedPointNum # The following routine creates an axis-label field containing string s. The location of the # field is relative to point pXLoc,pYLoc - which is normally the bottom (for x-ticks) or # left (for y-ticks) point in an axis tick mark. pXOrY is either "x" or "y". The optional # parameter tYColorsForScaleLabel can have color indications in different lines, # to set the colors of different lines s. A multi-line s only makes sense for y-axis scales. on makeAxisLabel pXOrY, pXLoc, pYLoc, s, pTextColors if pXOrY = "x" and (the graphXScaleVisible of me = "false") then exit makeAxisLabel if pXOrY = "y" and (the graphYScaleVisible of me = "false") then exit makeAxisLabel add 1 to aNumScaleLabelsCreated put "sl"& aNumScaleLabelsCreated into tFieldName if pXOrY = "x" then put "center" into tTA else put "right" into tTA put the graphScaleTextSize of me into tTS if tTS = "" then put 9 into tTS put tTS + min(0, round(the graphScaleTextSeparation of me)) into tTH if pXOrY = "x" then put 1 into tXFudge put 1 into tYFudge put round(pXLoc + tXFudge) into pXLocToUse put "" into pRightToUse put round(pYLoc + tYFudge) into pTopToUse else put 5 into tXFudge put -1 into tYFudge put "" into pXLocToUse put round(pXLoc + tXFudge) into pRightToUse put round(pYLoc + tYFudge - tTS/2) into pTopToUse end if put makeNumbersNiceForDisplay(s) into s makeAField tFieldName, s, tTA, the graphScaleTextFont of me, "", pTextColors, tTS, tTH, (pXLocToUse &",0"), "", pTopToUse, pRightToUse, "" if pXOrY = "x" then put the bottom of field tFieldName of me into aXScaleTextBottom end makeAxisLabel # Retun the passed string, ensuring that if it is a number -- or a series of numbers on separate # lines -- the number(s) display nicely. # A disadvantage of how I use this above is, I ought to give enough accuracy to display even # a tiny range between min & max scales. function makeNumbersNiceForDisplay pS put the graphScaleExponentHighThreshold of me into tLargeNumberToExpThreshold put the graphScaleExponentLowThreshold of me into tSmallNumberToExpThreshold put the graphScaleMinimumSignificantDigits of me into tMinimumSignificantDigits put the number of lines in pS into tNumLines repeat with i = 1 to tNumLines put line i of pS into s if s is a number then put s+0 into n if n = 0 then put "0" into s else if abs(n) < tSmallNumberToExpThreshold or abs(n) >= tLargeNumberToExpThreshold then put getMagnitude(n) into m if the graphScaleExponentFormat of me is "^" then put "*10^" into tExponentSeparator else put "e" into tExponentSeparator end if put round(n / 10^m, tMinimumSignificantDigits - 1) & tExponentSeparator & m into s #put format("%3.2g", n / 10^m) & tExponentSeparator & m into s else if n is an integer then put n into s else put getMagnitude(n) into m put min(0, m - (tMinimumSignificantDigits - 1)) into magnitudeAtWhichToRound put round(n, -magnitudeAtWhichToRound) into s #put format("%3.2g", n) into s end if end if put s into line i of pS end repeat return pS end makeNumbersNiceForDisplay # The following routine creates a field as specified. Parameter pFieldName must be unique # on each call. Parameters pTextSize and pTextHeight must be valid positive integers. To # set the location of the field, either pass the location in pLoc, or pass the horizontal location # in one of pLoc (the vertical location in pLoc is arbitrary) / pLeft / pRight and the vertical # location in one of pLoc (the horizontal location in pLoc is arbitrary) / pTop / pBottom. on makeAField pFieldName, pContents, pTextAlign, pTextFont, pTextStyle, pTextColors, pTextSize, pTextHeight, pLoc, pLeft, pTop, pRight, pBottom reset templateField set the threeD of the templateField to false set the showBorder of the templateField to false set the opaque of the templateField to false set the lockText of the templateField to true if pTextAlign <> "" then set the textAlign of the templateField to pTextAlign if pTextFont <> "" then set the textFont of the templateField to pTextFont set the textSize of the templateField to pTextSize # The textSize must be set after the textFont. set the textHeight of the templateField to pTextHeight if pTextStyle <> "" then set the textStyle of the templateField to pTextStyle put the number of lines in pContents into tNumLines put 10000 into h # Take a purposely too high guess at the necessary height to display the string. #put tNumLines * pTextHeight + 8 into h set the height of the templateField to h put 10000 into w # Take a purposely too high guess at the necessary width to display the string. # put maxLineLength(pContents) * pTextSize into w # if pTextStyle contains "bold" then multiply w by 2 set the width of the templateField to w set the autoTab of the templateField to false create field pFieldName in me put pContents into field pFieldName of me put the formattedHeight of field pFieldName of me into h set the height of field pFieldName of me to h put (the formattedWidth of field pFieldName of me) + 10 into w # The formattedWidth is actually not wide enough to deter word wrapping (perhaps because of margins?), so I add 10. set the width of field pFieldName of me to w if pLoc <> "" then set the loc of field pFieldName of me to pLoc if pLeft <> "" then set the left of field pFieldName of me to pLeft if pTop <> "" then set the top of field pFieldName of me to pTop if pRight <> "" then set the right of field pFieldName of me to pRight if pBottom <> "" then set the bottom of field pFieldName of me to pBottom if pTextColors <> "" then put the number of lines in pTextColors into n repeat with i = 1 to n set the textColor of line i of field pFieldName of me to line i of pTextColors end repeat end if end makeAField function maxLineLength pString put 0 into tMaxSoFar repeat for each line l in pString put length(l) into tLineLength if tLineLength > tMaxSoFar then put tLineLength into tMaxSoFar end repeat return tMaxSoFar end maxLineLength function nonBlankItems s put "" into r repeat for each item thisItem in s if thisItem <> "" then put thisItem &"," after r end repeat delete char -1 of r return r end nonBlankItems function graphMarkerLineToPoints s put word 1 of s into w1 if w1 = "" then put false into tFilled put "dot" into s else if w1 = "none" then return "" # No markers. exit graphMarkerLineToPoints else if w1 = "filled" or w1 = "solid" then put true into tFilled delete word 1 of s else if w1 = "empty" or w1 = "hollow" then put false into tFilled delete word 1 of s else #Default is hollow. put false into tFilled end if put word 1 of s into tSizeWord put word 2 of s into tTypeWord if tTypeWord = "" then put tSizeWord into tTypeWord put "small" into tSizeWord end if set the wholeMatches to true put wordOffset(tSizeWord, "tiny small medium large") into tSizeNumberFromWord if tSizeNumberFromWord > 0 then put word tSizeNumberFromWord of "0.1 0.25 0.5 1" into tSizeNumber else if (tSizeWord is a number) then put tSizeWord into tSizeNumber else put 0 into tSizeNumber end if put wordOffset(tTypeWord, "dot + x diamond square triangle circle") into tTypeNumber if tTypeNumber > 0 then if tTypeNumber = 1 then #Dot put "0,0 0,0" into tPoints else if tTypeNumber = 2 then #+ put "0,-12 0,12 -12,0 12,0" into tPoints else if tTypeNumber = 3 then #x put "-12,-12 12,12 -12,12 12,-12" into tPoints else if tTypeNumber = 4 then #Diamond put "0,-12 12,0 0,12 -12,0 0,-12" into tPoints else if tTypeNumber = 5 then #Square put "-12,-12 12,-12 12,12 -12,12 -12,-12" into tPoints else if tTypeNumber = 6 then #Triangle put "0,-12 12,12 -12,12 0,-12" into tPoints else if tTypeNumber = 7 then #Circle put "0,-12 2,-12 5,-11 7,-10 9,-9 10,-7 11,-5 12,-2 12,0 12,2 11,5 10,7 9,9 7,10 5,11 2,12 0,12 -2,12 -5,11 -7,10 -9,9 -10,7 -11,5 -12,2 -12,0 -12,-2 -11,-5 -10,-7 -9,-9 -7,-10 -5,-11 -2,-12 0,-12" into tPoints else if tSizeNumber > 0 or tSizeWord is a number then delete word 1 of s else put 1 into tSizeNumber end if put s into tPoints end if replace " " with cr in tPoints if tSizeNumber <> 1 then put tPoints into tPointsOriginal put "" into tPoints put the number of lines in tPointsOriginal into n repeat with i = 1 to n put line i of tPointsOriginal into l repeat with j = 1 to 2 put round(tSizeNumber * (item j of l)) into item j of l end repeat put l & cr after tPoints end repeat delete char -1 of tPoints #Delete trailing return. end if end if return tFilled & cr & tPoints end graphMarkerLineToPoints on ensurePropertiesOkay # graphAxisWidth if the graphAxisWidth of me is not an integer then set the graphAxisWidth of me to 2 else if the graphAxisWidth of me < 1 then set the graphAxisWidth of me to 1 end if # graphMainRect put the graphMainRect of me into tGMR if tGMR <> "" then put tGMR into tGMRInit put the number of items in tGMR into n if n < 4 then put "" into tGMR else if n > 4 then put item 1 to 4 of tGMR into tGMR else repeat for each item tItem in tGMR if not (tItem is an integer) then put "" into tGMR exit repeat end if end repeat end if end if if tGMR = "" then put the rect of me into tGMR if tGMR <> tGMRInit then set the graphMainRect of me to tGMR # Data - ensure no spaces and no "NaN" values. put the graphX of me into tGX replace " " with "" in tGX replace "NaN" with "" in tGX set the graphX of me to tGX put the graphY of me into tGY replace " " with "" in tGY replace "NaN" with "" in tGY set the graphY of me to tGY # Tic widths. put the graphTickMajorWidth of me into tGTMW if not (tGTMW is an integer) then if tGTMW is a number then put round(tGTMW) into tGTMW else put 4 into tGTMW end if set the graphTickMajorWidth of me to tGTMW end if # Tick labels. put the graphScaleMinimumSignificantDigits of me into tMSD if tMSD is not a number then set the graphScaleMinimumSignificantDigits of me to 3 else if tMSD < 1 then set the graphScaleMinimumSignificantDigits of me to 1 else if tMSD is not an integer then set the graphScaleMinimumSignificantDigits of me to (trunc(tMSD) + 1) end ensurePropertiesOkay on setDefaultProperties set the graphAxisWidth of me to 1 set the graphClickable of me to "false" set the graphEditable of me to "false" set the graphKeyLogIndicator of me to "[logarithmic]" set the graphKeyTextFont of me to "" set the graphKeyTextSeparation of me to 3 set the graphKeyTextSize of me to 10 set the graphKeyXNudge of me to 0 set the graphKeyYNudge of me to 0 set the graphLineColors of me to "" set the graphLineDashes of me to "" set the graphLinesVisible of me to "true" set the graphLineWidths of me to "" set the graphMainRect of me to 50,50,250,150 set the graphMarkers of me to "" set the graphScaleExponentFormat of me to "^" set the graphScaleExponentHighThreshold of me to 100000 set the graphScaleExponentLowThreshold of me to 0.001 set the graphScaleMinimumSignificantDigits of me to 3 set the graphScaleTextSeparation of me to 3 set the graphScaleTextSize of me to 9 set the graphScaleTextFont of me to "" set the graphSendEditMessage of me to false set the graphTickMajorWidth of me to 4 set the graphTitle of me to "" set the graphTitleGap of me to 10 set the graphTitleTextFont of me to "" set the graphTitleTextSize of me to 12 set the graphTitleTextStyle of me to "plain" set the graphX of me to "0,1,2,3,4,5" set the graphXLabel of me to "" set the graphXLabelXNudge of me to 0 set the graphXLabelYNudge of me to 0 set the graphXLog of me to false set the graphXMax of me to "" set the graphXMin of me to "" set the graphXRound of me to false set the graphXScaleVisible of me to true set the graphXTicks of me to "" set the graphXTicksInset of me to false set the graphXTicksVisible of me to true set the graphXYLabelTextFont of me to "" set the graphXYLabelTextSize of me to 9 set the graphY of me to "0,1,2,3,4,5" set the graphYDataEdited of me to "" set the graphYLabel of me to "" set the graphYLabelXNudge of me to 0 set the graphYLabelYNudge of me to 0 set the graphYLog of me to false set the graphYMax of me to "" set the graphYMin of me to "" set the graphYRound of me to false set the graphYScaleSame of me to true set the graphYScaleVisible of me to true set the graphYTicks of me to "" set the graphYTicksInset of me to false set the graphYTicksVisible of me to true set the graphYUnitsOfMeasureInKey of me to "" set the graphYVariableNames of me to "" set the graphYScalesInKey of me to true end setDefaultProperties # The following handlers are used to come up with ranges for graphs. # Included are handlers for scaling numbers & for making them easily readable. # Round the range to use for a graph. Give this min. and max. numbers (in that order) # separated by a comma. This returns the new rounded min. and max., again separated # by a comma. The third argument is true if natural logarithms of the numbers have been # taken but the original numbers (the exponents of the logged numbers) will be displayed. function roundRange pMin, pMax, pLogged put pMin into tMin put pMax into tMax if pLogged <> "true" then if tMin = tMax then put roundDown( ln(abs(tMin)) / 2.3025850929941 ) into magnitude if tMin = 0 then put -1 into tMin put 1 into tMax else if tMin > 0 then put 0 into tMin put 2 * roundUpToMagnitude(tMax, magnitude) into tMax else -- tMin < 0 put 2 * roundDownToMagnitude(tMin, magnitude) into tMin put 0 into tMax end if else put roundDown( ln(abs(tMax - tMin)) / 2.3025850929941 ) into magnitude put roundDownToMagnitude(tMin, magnitude) into tMin put roundUpToMagnitude(tMax, magnitude) into tMax end if else # Deal with the logarithmic case. if tMin = tMax then put tMin - exp(1)/10 into tMin put tMin + exp(1)/10 into tMax else put getMagnitude(tMin) into tMinMagnitude put round(tMin, 1 - tMinMagnitude) into tMinTRounded if tMinTRounded > tMin then put tMinTRounded - 10^(tMinMagnitude - 1) into tMinTRounded put tMinTRounded into tMin put getMagnitude(tMax) into tMaxMagnitude put round(tMax, 1 - tMaxMagnitude) into tMaxTRounded if tMaxTRounded < tMax then put tMaxTRounded + 10^(tMaxMagnitude - 1) into tMaxTRounded put tMaxTRounded into tMax end if end if return tMin &","& tMax end roundRange -- Create a version of the range in readable form. function displayRange pMin, pMax return readableNumber(pMin) &" to "& readableNumber(pMax) end displayRange function readableTwoDigit n return readableNumber(roundToTwoDigits(n)) end readableTwoDigit -- Round to 2 digits of accuracy. function roundToTwoDigits n put getMagnitude(n) into magnitude put 10 ^ (magnitude - 1) into scalingNumber return round( n / scalingNumber ) * scalingNumber end roundToTwoDigits function readableNumber pN put pN + 0 into n if n = 0 then return "0" else put roundDown( ln(abs(n)) / 2.3025850929941 ) into magnitude if magnitude >= 3 and magnitude <= 20 then put magnitude div 3 into powerOfThousand put item powerOfThousand of "thousand,million,billion,trillion,quadrillion,quintillion" into s put 1000 into divisor repeat with i = 2 to powerOfThousand put divisor * 1000 into divisor end repeat put n / divisor into displayN -- if displayN > 0 and displayN < 10 then -- if displayN is an integer then -- put item displayN of "one,two,three,four,five,six,seven,eight,nine" into displayN -- end if -- end if return displayN && s else if magnitude >= -3 and magnitude <= 2 then return n else return (n / 10 ^ magnitude) &" * 10 ^ "& magnitude end if end if end readableNumber function getMagnitude n return roundDown( log10(abs(n)) ) end getMagnitude function roundDownToMagnitude n, magnitude put 10^magnitude into scalingFactor return scalingFactor * roundDown( n / scalingFactor ) end roundDownToMagnitude function roundDown n put trunc( n ) into m if n >= 0 then return m else if n = m then return n else return m - 1 end if end roundDown function roundUpToMagnitude n, magnitude put 10^magnitude into scalingFactor return scalingFactor * roundUp( n / scalingFactor ) end roundUpToMagnitude function roundUp n put trunc( n ) into m if n <= 0 then return m else if n = m then return n else return m + 1 end if end roundUp function roundToMagnitude n, magnitude put 10^magnitude into scalingFactor return scalingFactor * round( n / scalingFactor ) end roundToMagnitude function chooseTickLocs pMin, pMax, pApproxNum, pExactNum put pMin into tMin put pMax into tMax put tMax - tMin into tDiff if pExactNum <> "" then put round(min(max(pExactNum,2),50)) into tNumTicksToUse #Force to be between 2 and 50. else # Choose how many tick marks to use. put round(min(max(pApproxNum,2),50)) into tApproxNum #Force to be between 2 and 50. put 0 into tNumTicksToUse put 0 into tNumTicksToUsePriority2 put 0 into tNumTicksToUsePriority3 put 0 into tNumTicksToUsePriority4 put tDiff / 10^getMagnitude(tDiff) into tDiffInOnesUnits put roundUp(pApproxNum*0.66) into tMinNumTicks put roundDown(pApproxNum*1.515152) into tMaxNumTicks repeat with i = tMinNumTicks to tMaxNumTicks put (i-1) into tNumSteps put round(tDiffInOnesUnits / tNumSteps,4) into tStep if tStep = round(tStep,0) then # This number of tick marks gives a nice round number for the length between tick marks. if tNumTicksToUse = 0 then put i into tNumTicksToUse else if abs(i / tApproxNum - 1) < abs(tNumTicksToUse / tApproxNum - 1) then put i into tNumTicksToUse end if if i >= tApproxNum then exit repeat # The optimal number of ticks has been founded; never choose a higher number than necessary above the "about" number to achieve round-number distances. end if else if tStep = round(tStep,1) then # This number of tick marks gives a fairly nice round number for the length between tick marks. if tNumTicksToUsePriority2 = 0 then put i into tNumTicksToUsePriority2 else if abs(i / tApproxNum - 1) < abs(tNumTicksToUsePriority2 / tApproxNum - 1) then put i into tNumTicksToUsePriority2 end if else if tStep = round(tStep,2) then # This number of tick marks gives a somewhat round number for the length between tick marks. if tNumTicksToUsePriority3 = 0 then put i into tNumTicksToUsePriority3 else if abs(i / tApproxNum - 1) < abs(tNumTicksToUsePriority3 / tApproxNum - 1) then put i into tNumTicksToUsePriority3 end if else if tStep = round(tStep,3) then # This number of tick marks gives a somewhat round number for the length between tick marks. if tNumTicksToUsePriority4 = 0 then put i into tNumTicksToUsePriority4 else if abs(i / tApproxNum - 1) < abs(tNumTicksToUsePriority4 / tApproxNum - 1) then put i into tNumTicksToUsePriority4 end if end if end repeat if tNumTicksToUse = 0 then if tNumTicksToUsePriority2 > 0 then put tNumTicksToUsePriority2 into tNumTicksToUse # Use a fairly-round distance between ticks. else if tNumTicksToUsePriority3 > 0 then put tNumTicksToUsePriority3 into tNumTicksToUse # Use a slightly-round distance between ticks. else if tNumTicksToUsePriority4 > 0 then put tNumTicksToUsePriority4 into tNumTicksToUse # Use a marginally-round distance between ticks. else put tApproxNum into tNumTicksToUse # Couldn't find a round distance between ticks. end if end if end if # Determine the tick mark locations. put "" into tR put tDiff / (tNumTicksToUse - 1) into tStep repeat with i = 1 to tNumTicksToUse if i < tNumTicksToUse then put (tMin + (i - 1) * tStep) &"," after tR else put tMax after tR end repeat return tR end chooseTickLocs # Handle editing of the graph. on graphCoverClicked # Get info needed to control editing. put the left of button "graph cover" of me into tXLeft put the right of button "graph cover" of me into tXRight put the top of button "graph cover" of me into tYTop put the bottom of button "graph cover" of me into tYBottom put the cpEditCurveNum of button "graph cover" of me into tCurveNum put the points of graphic ("curve "& tCurveNum) of me into tPoints put tPoints into tPointsOriginal put (the cpXDataRanges of button "graph cover" of me) into tXValRanges # Do the editing - loop while the mouse is down.. repeat while the mouse is down # Get the mouse location, constrained on the y-axis to the plot region. put the mouseLoc into tMouseLoc put item 1 of tMouseLoc into tMouseX put max(min(item 2 of tMouseLoc, tYBottom), tYTop) into tMouseY # Revise the curve based on the mouse location. if tMouseX >= (tXLeft - 6) and tMouseX <= (tXRight + 6) then # 6 is the amount to left or right of graph where editing still occurs. # Loop through points on the curve. put 0 into tPointNum repeat for each line tXVR in tXValRanges add 1 to tPointNum put item 1 of tXVR into tMinOwnedRange if tMinOwnedRange = "" then next repeat # Ignore line segment in key. if tMinOwnedRange <> "-INF" then if tMouseX < tMinOwnedRange then next repeat end if put item 2 of tXVR into tMaxOwnedRange if tMaxOwnedRange <> "+INF" then if tMouseX > tMaxOwnedRange then next repeat end if put tMouseY into item 2 of line tPointNum of tPoints set the points of graphic ("curve "& tCurveNum) of me to tPoints end repeat end if end repeat # The mouse button is no longer down. Update y-data based on the edited graph. if tPoints <> tPointsOriginal then put tYBottom - tYTop into tYDiff put the cpGraphYMin of button "graph cover" of me into tYValsMin put the cpGraphYMax of button "graph cover" of me into tYValsMax put tYValsMax - tYValsMin into tYValsDiff put the number of lines in tXValRanges into tNumPoints put "" into tNewYData put 0 into tPointNum repeat for each line tP in tPoints add 1 to tPointNum if tP = tNumPoints then exit repeat # The curve may have more points, but they belong to the line segment in the key, and must not be edited. put item 2 of tP into tPY put tYValsMin + tYValsDiff * (tYBottom - tPY) / tYDiff into tYVal put tYVal &"," after tNewYData end repeat delete the last char of tNewYData # Delete trailing comma. repeat for each item tDuplicatedPointNum in aDuplicatedPointNums # These have already been sorted in reverse order. delete item tDuplicatedPointNum of tNewYData # Some points may have been duplicated for internal purposes, to ensure graphs can be drawn correctly when there is only one datum, but the user must not be passed back data that include duplicates. end repeat set the graphYDataEdited of me to tNewYData if (the graphSendEditMessage of me) = "true" then send "graphEdited" to this card end if end graphCoverClicked # Given a string of lines each containing an x-value as its first (comma-separated) item, return a comma-separated list of the x-values. function getXVals pS put "" into tR repeat for each line tL in pS put (item 1 of tL) &"," after tR end repeat delete char -1 of tR return tR end getXVals # Given a list of x-data, return "owned" ranges around each data point, i.e. the x-values for which the nearest data point is each point. # The result will be a string with one line of comma-separated data for each x-data point. In each line, the first item is the minimum owned # and the second item is the maximum owned value. "-INF" or "+INF" is used where the minimum or maximum owned value is negative # or positive infinity. function clickXRanges pXData # Get the x-data in sorted order. put nonBlankItems(pXData) into tXDataSorted sort items of tXDataSorted numeric # In case of small round-off errors in numbers, ensure that the min. and max. parameters are not inside the x data points. put item 1 of tXDataSorted into tXMin put item -1 of tXDataSorted into tXMax # Prepare lists of the relevant min. and max. values, by looping through each data point and adding its information to the lists. put "" into tRangesOwned repeat for each item tN in pXData if tN = "" then put "" into tThisRangeMinOwned put "" into tThisRangeMaxOwned else # Find the greatest point below this x-value, or the overall min. if no points are below. put tXMin into tThisRangeMin repeat for each item tSortedN in tXDataSorted if tSortedN < tN then put tSortedN into tThisRangeMin else exit repeat end repeat # Find the smallest point above this x-value, or the overall max. if no points are above. if (item -1 of tXDataSorted) = tN then put tXMax into tThisRangeMax else repeat for each item tSortedN in tXDataSorted if tSortedN > tN then put tSortedN into tThisRangeMax exit repeat end if end repeat end if # In the range just found, if the point is in between other points, half the ranges belongs to this point and half to other points. if tN=tXMin then put "-INF" into tThisRangeMinOwned else put (tN + tThisRangeMin) / 2 into tThisRangeMinOwned end if if tN=tXMax then put "+INF" into tThisRangeMaxOwned else put (tThisRangeMax + tN) / 2 into tThisRangeMaxOwned end if end if # Add information to the lists of ranges owned. put tThisRangeMinOwned &","& tThisRangeMaxOwned & cr after tRangesOwned # Use &","& tN to include the x-value as well. end repeat delete char -1 of tRangesOwned if (char -1 of pXData) = "," then put cr &"," after tRangesOwned #The trailing comma corresponds to a blank item. return tRangesOwned end clickXRanges # Given a list of items, take the natural logarithm of all nonblank items. function listLn s put "" into r repeat for each item tItem in s if tItem <> "" then put ln(tItem) into tItem put tItem &"," after r end repeat delete char -1 of r return r end listLn # Given a list of items, if exactly one is non-null then return the item number, else return null. function singleNonmissingItemNum s put "" into tR put 0 into i repeat for each item tItem in s add 1 to i if tItem <> "" then if tR = "" then put i into tR else put "" into tR exit repeat end if end if end repeat return tR end singleNonmissingItemNum on createGraphic pName put the lockMessages into tOrigLockMessages set the lockMessages to true # Revolution has a "feature" that alters small graphic objects, but we don't want that here. create graphic pName in me set the lockMessages to tOrigLockMessages end createGraphic . ± <graphLineDashes graphYRound falsegraphLinesVisible truegraphYTicksInset falsegraphEditable falsegraphLineWidths graphXLabelXNudge 0 graphXMin graphSendEditMessage falsegraphYLabelYNudge 6 graphXMax graphXScaleVisible truegraphXTicks graphScaleExponentFormat ^graphMainRect 50,80,250,180graphKeyXNudge 0graphKeyLogIndicator [logarithmic]graphYLabel !Major oil tanker spills worldwidegraphXYLabelTextSize 12graphTitleTextSize 12graphYVariableNames graphYTicksVisible truegraphXYLabelTextFont graphMarkers tiny +graphAxisWidth 1graphTitleTextFont graphYScaleSame truegraphScaleTextSize 9graphTitleTextStyle plaingraphXRound falsegraphClickable falsegraphTitle graphScaleTextSeparation 3graphYLabelXNudge 0graphScaleTextFont graphYMin graphScaleExponentHighThreshold 100000 graphYMax graphXLog falsegraphLineColors redgraphYScaleVisible truegraphXLabel YeargraphYDataEdited graphTitleGap 10graphKeyTextSeparation 3graphXLabelYNudge -18#graphScaleMinimumSignificantDigits 3graphYTicks graphXTicksInset falsegraphYScalesInKey truegraphXTicksVisible truegraphKeyYNudge 0graphScaleExponentLowThreshold 0.001graphX r1975,1976,1977,1978,1979,1980,1981,1982,1983,1984,1985,1986,1987,1988,1989,1990,1991,1992,1993,1994,1995,1996,1997graphY .8,6,6,6,11,4,2,0,5,0,2,0,0,0,3,0,2,1,1,2,1,1,2graphKeyTextSize 10 graphYLog falsegraphYUnitsOfMeasureInKey graphTickMajorWidth 4graphKeyTextFont cREVGeneral scriptChecksum Żķ7{Õ°Ų¦b “ bookmarks revUniqueID 1166423936976breakPoints handlerList ¶makeGraph noteDuplicatedPointNum makeAxisLabel makeNumbersNiceForDisplay makeAField maxLineLength nonBlankItems graphMarkerLineToPoints ensurePropertiesOkay setDefaultProperties roundRange displayRange readableTwoDigit roundToTwoDigits readableNumber getMagnitude roundDownToMagnitude roundDown roundUpToMagnitude roundUp roundToMagnitude chooseTickLocs graphCoverClicked getXVals clickXRanges listLn singleNonmissingItemNum createGraphicscriptSelection char 14644 to 14643prevHandler chooseTickLocstempScript script ö# Copyright (c) Kenneth L. Simons 2000-2003.
# All Rights Reserved.
# The author hereby allows others to use the graph object according to the following principles:
# Anyone may use the graph object for any purpose.
# Rights to use of the original object must remain in the public domain.
local aNumScaleLabelsCreated
local aXScaleTextBottom
local aDuplicatedPointNums
on makeGraph
# 1. Ensure (some of the) properties are okay.
ensurePropertiesOkay
# 2. Get/Calculate subsidiary information.
# 2a. Main graph coordinates.
put the graphMainRect of me into tGMR
set the rect of button "graph background" of me to tGMR
put item 1 of tGMR into a # Left side coordinate of main graph.
put item 4 of tGMR into b # Bottom coordinate of main graph.
put (item 3 of tGMR) - a into w # Width of main graph.
put b - (item 2 of tGMR) into h # Height of main graph.
# 2b. Data and axis scales.
put "" into aDuplicatedPointNums
put the graphX of me into tXData
put singleNonmissingItemNum(tXData) into tSingleNonmXItemN
if tSingleNonmXItemN <> "" then
put ","& (item tSingleNonmXItemN of tXData) after item tSingleNonmXItemN of tXData # If only one data point, make 2 identical DPs for correct graphing.
noteDuplicatedPointNum tSingleNonmXItemN
end if
put the number of items in tXData into tNumXPoints
if (char -1 of tXData) = "," then add 1 to tNumXPoints # Include the blank item at the end.
put nonBlankItems(tXData) into tXDataNonBlank # Used when finding min and max.
put min(tXDataNonBlank) into tXMin
if (the graphXMin of me) <> "" then put min(the graphXMin of me,tXMin) into tXMin
put max(tXDataNonBlank) into tXMax
if (the graphXMax of me) <> "" then put max(the graphXMax of me,tXMax) into tXMax
put (tXMin = "" or tXMin > 0) and (the graphXLog of me = true) into tXLogarithmic
if tXLogarithmic then
put listLn(tXData) into tXData
if tXMin <> "" then put ln(tXMin) into tXMin
if tXMax <> "" then put ln(tXMax) into tXMax
end if
if (the graphXRound of me) = "true" then
put roundRange(tXMin, tXMax, tXLogarithmic) into tRoundedXRange
put item 1 of tRoundedXRange into tXMin
put item 2 of tRoundedXRange into tXMax
end if
if tXMin = tXMax then
if tXMin = 0 then
put -1 into tXMin
put 1 into tXMax
else if tXMin > 0 then
put tXMin * 2 into tXMax
put 0 into tXMin
else
put 0 into tXMax
put tXMin * 2 into tXMin
end if
end if
put (the number of lines in the graphY of me) into tNumCurves
repeat with i = 1 to tNumCurves
put line i of the graphY of me into tYData[i] # In general this is a line of multiple numbers (so don't use format).
end repeat
repeat with i = 1 to tNumCurves
if tSingleNonmXItemN <> "" then
if (the number of items in tYData[i]) >= tSingleNonmXItemN then # This if-then is not crucial, but better with very many data points.
put ","& item tSingleNonmXItemN of tYData[i] after item tSingleNonmXItemN of tYData[i] # Duplicate a data point, because it has been duplicated (for correct graphing) in the x-data.
end if
end if
put singleNonmissingItemNum(tYData[i]) into tSingleNonmYItemN
if tSingleNonmYItemN <> "" then # If only one data point, make 2 identical DPs for correct graphing.
put ","& (item tSingleNonmYItemN of tXData) after item tSingleNonmYItemN of tXData
add 1 to tNumXPoints
repeat with j = 1 to tNumCurves
put ","& (item tSingleNonmYItemN of tYData[j]) after item tSingleNonmYItemN of tYData[j]
end repeat
noteDuplicatedPointNum tSingleNonmYItemN
end if
put nonBlankItems(tYData[i]) into thisYDataNonBlank # Used when finding min and max.
put line i of the graphYMin of me into tThisGraphYMin
put format("%14.12e", min(thisYDataNonBlank)) into tYMin[i]
if tThisGraphYMin <> "" then put format("%14.12e", min(tThisGraphYMin,tYMin[i])) into tYMin[i]
put line i of the graphYMax of me into tThisGraphYMax
put format("%14.12e", max(thisYDataNonBlank)) into tYMax[i]
if tThisGraphYMax <> "" then put format("%14.12e", max(tThisGraphYMax,tYMax[i])) into tYMax[i]
end repeat
repeat with i = 1 to tNumCurves
put (tYMin[i] = "" or tYMin[i] > 0) and ((the graphYLog of me) = "true" or (line i of the graphYLog of me) = true) into tYLogarithmic[i]
if tYLogarithmic[i] then
put listLn(tYData[i]) into tYData[i]
if tYMin[i] <> "" then put ln(tYMin[i]) into tYMin[i]
if tYMax[i] <> "" then put ln(tYMax[i]) into tYMax[i]
end if
end repeat
put the graphYScaleSame of me into tYScalesSame # Determine whether y-scales forced to be the same.
if tYScalesSame = true then # Disallow y-scales same if some logarithmic, some not.
repeat with i = 2 to tNumCurves
if tYLogarithmic[i] <> tYLogarithmic[1] then
put false into tYScalesSame
exit repeat
end if
end repeat
end if
if tYScalesSame = "true" then # A single ymin and ymax scale for all curves.
put tYMin[1] into tYMinAll
put tYMax[1] into tYMaxAll
repeat with i = 2 to tNumCurves
put min(tYMinAll,tYMin[i]) into tYMinAll
put max(tYMaxAll,tYMax[i]) into tYMaxAll
end repeat
if tYMinAll = tYMaxAll then
if tYMinAll = 0 then
put -1 into tYMinAll
put 1 into tYMaxAll
else if tYMinAll > 0 then
put tYMinAll * 2 into tYMaxAll
put 0 into tYMinAll
else
put 0 into tYMaxAll
put tYMinAll * 2 into tYMinAll
end if
end if
if (the graphYRound of me) = "true" then
put roundRange(tYMinAll, tYMaxAll, tYLogarithmic[1]) into tRoundedYRange
put item 1 of tRoundedYRange into tYMinAll
put item 2 of tRoundedYRange into tYMaxAll
end if
put format("%14.12e", tYMinAll) into tYMinAll
put format("%14.12e", tYMaxAll) into tYMaxAll
repeat with i = 1 to tNumCurves
put tYMinAll into tYMin[i]
put tYMaxAll into tYMax[i]
end repeat
else # Different ymin and ymax scales for different curves.
if (the graphYRound of me) = "true" then
repeat with i = 1 to tNumCurves
put roundRange(tYMin[i], tYMax[i], tYLogarithmic[i]) into tRoundedYRange
put format("%14.12e", item 1 of tRoundedYRange) into tYMin[i]
put format("%14.12e", item 2 of tRoundedYRange) into tYMax[i]
end repeat
else
repeat with i = 1 to tNumCurves
if tYMin[i] = tYMax[i] then
if tYMin[i] = 0 then
put -1 into tYMin[i]
put 1 into tYMax[i]
else if tYMin[i] > 0 then
put tYMin[i] * 2 into tYMax[i]
put 0 into tYMin[i]
else
put 0 into tYMax[i]
put tYMin[i] * 2 into tYMin[i]
end if
end if
end repeat
end if
end if
# 2c. Whether the y-axis scales for multiple variables are the same.
if tYScalesSame <> "true" then
put true into tYScalesSame # Assume same until proven different.
repeat with i = 2 to tNumCurves
if tYMin[i] <> tYMin[1] or tYMax[i] <> tYMax[1] then
put false into tYScalesSame
exit repeat
end if
end repeat
end if
# 2d. Scaling factors for plotting data.
put w / (tXMax - tXMin) into tXScaleFactor
repeat with i = 1 to tNumCurves
put format("%14.12e", h / (tYMax[i] - tYMin[i])) into tYScaleFactor[i]
end repeat
# 2f. X and Y values at which to plot tic marks.
if the graphXTicks of me = "none" then
put "" into tXTickLocs
else if (word 1 of the graphXTicks of me) = "about" then
put chooseTickLocs(tXMin, tXMax,(word 2 of the graphXTicks of me),"") into tXTickLocs
else if (word 1 of the graphXTicks of me) = "exactly" or (word 1 of the graphXTicks of me) = "exact" then
put chooseTickLocs(tXMin, tXMax,"",(word 2 of the graphXTicks of me)) into tXTickLocs
else if the graphXTicks of me <> "" then
put the graphXTicks of me into tXTickLocs
else
put tXMin &","& tXMax into tXTickLocs
end if
if the graphYTicks of me = "none" then
put "" into tYTickLocs
else if (word 1 of the graphYTicks of me) = "about" then
put chooseTickLocs(tYMin[1], tYMax[1],(word 2 of the graphYTicks of me),"") into tYTickLocs
else if (word 1 of the graphYTicks of me) = "exactly" or (word 1 of the graphYTicks of me) = "exact" then
put chooseTickLocs(tYMin[1], tYMax[1],"",(word 2 of the graphYTicks of me)) into tYTickLocs
else if the graphYTicks of me <> "" then
put the graphYTicks of me into tYTickLocs
else
put tYMin[1] &","& tYMax[1] into tYTickLocs # Y tic locs are defined in terms of the first y variable only.
end if
# 3. Lock the screen before doing anything that affects the display.
lock screen
# 4. Delete existing graphics and fields in this graph object, and the "graph cover" button if any.
put the number of graphics in me into nGraphics
repeat with i = nGraphics down to 1
delete graphic i of me
end repeat
put the number of fields in me into nFields
repeat with i = nFields down to 1
delete field i of me
end repeat
if there is a button "graph cover" of me then delete button "graph cover" of me
# 5. Draw axes.
reset templateGraphic
set the style of the templateGraphic to "polygon"
set the lineSize of the templateGraphic to the graphAxisWidth of me
set the points of the templateGraphic to a &","& (b-h) & cr & a &","& b & cr & (a+w) &","& b
createGraphic "axes"
put a &","& (b-h) &","& (a+w) &","& b into tGraphCoverRect # May be used below, for editable graphs.
# 6. Draw tick marks.
# 6a. Draw major tick marks and labels.
put "" into aXScaleTextBottom
put 0 into aNumScaleLabelsCreated
put "" into tTickPoints
put tXTickLocs <> "" and (the graphXTicksVisible of me) <> "false" into tXTicksVisible
put tXTickLocs <> "" and (the graphXScaleVisible of me) <> "false" into tXScaleVisible
if tXTicksVisible or tXScaleVisible then
if the graphXTicksInset of me = "true" or (not tXTicksVisible) then
put the graphTickMajorWidth of me into tTickOffset
else
put 0 into tTickOffset
end if
repeat for each item thisXLoc in tXTickLocs
put round(a + (thisXLoc - tXMin) * tXScaleFactor) into thisXWindowLoc
put b + (the graphTickMajorWidth of me) - tTickOffset into tYAtBottomOfTick
if tXTicksVisible then put thisXWindowLoc &","& (b-tTickOffset) & cr & thisXWindowLoc &","& tYAtBottomOfTick & cr & cr after tTickPoints
if tXScaleVisible then
if tXLogarithmic then put exp(thisXLoc) into thisXLoc
makeAxisLabel "x", thisXWindowLoc, tYAtBottomOfTick, thisXLoc
end if
end repeat
end if
put tYTickLocs <> "" and (the graphYTicksVisible of me) <> "false" into tYTicksVisible
put the graphYScaleVisible of me into tGYSVOM
if tGYSVOM = "true" then
if not tYScalesSame then # When the graphYScaleVisible is true and there are multiple curves with different scales, display scales for each.
put "" into tGYSVOM
repeat with i = 1 to tNumCurves
put i &"," after tGYSVOM
end repeat
delete the last char of tGYSVOM #Delete trailing comma.
end if
end if
put tYTickLocs <> "" and tGYSVOM <> "false" into tYScaleVisible
if tYTicksVisible or tYScaleVisible then
if the graphYTicksInset of me = "true" or (not tYTicksVisible) then
put the graphTickMajorWidth of me into tTickOffset
else
put 0 into tTickOffset
end if
repeat for each item thisYLoc in tYTickLocs # Step through different tick marks. (Recall that tYTickLocs is defined only in terms of the first y-variable.)
put round(b - (thisYLoc - tYMin[1]) * tYScaleFactor[1]) into thisYWindowLoc
put a - the graphTickMajorWidth of me + tTickOffset into tXAtLeftOfTick
if tXTicksVisible then put tXAtLeftOfTick &","& thisYWindowLoc & cr & (a + tTickOffset) &","& thisYWindowLoc & cr & cr after tTickPoints
if tYScaleVisible then
if tGYSVOM = "true" then
if tYLogarithmic[1] then put exp(thisYLoc) into tYLocsForScaleLabel
else put thisYLoc into tYLocsForScaleLabel
put "" into tYColorsForScaleLabel
else
if thisYLoc = tYMax[1] then put 1 into tYFrac
else put (thisYLoc - tYMin[1]) / (tYMax[1] - tYMin[1]) into tYFrac
put "" into tYLocsForScaleLabel
put "" into tYColorsForScaleLabel
put the number of items in tGYSVOM into n
repeat with i = 1 to n # Step through different curves.
put item i of tGYSVOM into thisCurveNum
put tYMin[thisCurveNum] into tThisMin
put tYMax[thisCurveNum] - tThisMin into tThisDiff
if tYFrac = 1 then put tYMax[thisCurveNum] into tThisY #Avoid rounding error.
else put tThisMin + tThisDiff * tYFrac into tThisY
if tYLogarithmic[i] then put exp(tThisY) into tThisY
put tThisY & return after tYLocsForScaleLabel
put line i of the graphLineColors of me into tGC
if tGC = "" then put the effective foregroundColor of me into tGC
put tGC & return after tYColorsForScaleLabel
end repeat
delete the last char of tYLocsForScaleLabel #Delete trailing return.
delete the last char of tYColorsForScaleLabel #Delete trailing return.
end if
makeAxisLabel "y", tXAtLeftOfTick, thisYWindowLoc, tYLocsForScaleLabel, tYColorsForScaleLabel
end if
end repeat
end if
if tXTicksVisible or tYTicksVisible then
reset templateGraphic
set the style of the templateGraphic to "polygon"
set the points of the templateGraphic to tTickPoints
createGraphic "ticks"
end if
# 7. Draw data.
repeat with i = 1 to tNumCurves
put tYScaleFactor[i] into thisYScaleFactor
reset templateGraphic
set the style of the templateGraphic to "polygon"
if (line i of the graphLinesVisible of me) = "false" then put 0 into tGLW
else put line i of the graphLineWidths of me into tGLW
if tGLW is an integer then set the lineSize of the templateGraphic to tGLW
put "" into tPoints
repeat with j = 1 to tNumXPoints
put item j of tXData into x
put item j of tYData[i] into y
if x = "" or y = "" then put cr after tPoints
else put round(a + (x - tXMin) * tXScaleFactor) &","& round(b - (y - tYMin[i]) * thisYScaleFactor) & cr after tPoints
end repeat
delete char -1 of tPoints # Delete trailing return.
set the points of the templateGraphic to tPoints
put line i of the graphLineColors of me into tGC
if tGC <> "" then set the foregroundColor of the templateGraphic to tGC
put line i of the graphLineDashes of me into tGD
if tGD <> "" then set the dashes of the templateGraphic to tGD
if the graphClickable of me = "true" then
set the script of the templateGraphic to "on mouseUp"& cr &" graphClicked "& i &", ((item 1 of the clickLoc) - "& a &") / "& tXScaleFactor &" + "& tXMin &", ("& b &" - (item 2 of the clickLoc)) / "& thisYScaleFactor &" + "& tYMin[i] & cr &"end mouseUp"
end if
put graphMarkerLineToPoints(line i of the graphMarkers of me) into tGM
if tGM <> "" then
put line 1 of tGM into tGMFilled
put line 2 to -1 of tGM into tGMPoints
set the markerDrawn of the templateGraphic to true
set the markerFilled of the templateGraphic to tGMFilled
set the markerPoints of the templateGraphic to tGMPoints
if tGC <> "" then
set the markerColor of the templateGraphic to tGC
set the markerFillColor of the templateGraphic to tGC
end if
end if
createGraphic "curve "& i
end repeat
# 8. Title.
put the graphTitle of me into tMainTitle
if tMainTitle <> "" then
put the graphTitleTextSize of me into tTS
if tTS = "" then put 12 into tTS
put tTS + 4 into tTH
put round(((item 1 of tGMR)+(item 3 of tGMR))/2) into tXLoc
put round((item 2 of tGMR) - (the graphTitleGap of me)) into tBottom
makeAField "title", tMainTitle, "center", the graphTitleTextFont of me, the graphTitleTextStyle of me, "", tTS, tTH, (tXLoc &","& 0), "", "", "", tBottom
end if
# 9. Axis variable/label names.
put the graphXYLabelTextSize of me into tTS
if tTS = "" then put 9 into tTS
put tTS + 4 into tTH
put the graphXLabel of me into tGXL
if tGXL <> "" then
put round(((item 1 of tGMR)+(item 3 of tGMR))/2) + (the graphXLabelXNudge of me) into tXLoc
if tXTicksVisible then
put the graphTickMajorWidth of me into tYOffset
else
put 0 into tYOffset
end if
if aXScaleTextBottom <> "" then
put aXScaleTextBottom - 1 into tTopOfField
else
put (item 4 of tGMR) + tYOffset - 1 into tTopOfField
end if
add the graphXLabelYNudge of me to tTopOfField
makeAField "x varname", tGXL, "center", the graphXYLabelTextFont of me, "", "", tTS, tTH, (tXLoc &","& 0), "", tTopOfField, "", ""
put the bottom of field "x varname" of me into tXLabelingBottom # Used when making a key.
else
# No x-axis label was created.
if aXScaleTextBottom <> "" then
put aXScaleTextBottom into tXLabelingBottom # Used when making a key.
else
put b into tXLabelingBottom # Used when making a key.
end if
end if
put the graphYLabel of me into tGYL
if tGYL <> "" then
# The left and bottom chosen here are quite arbitrary; there are certainly better methods to choose them.
put (item 1 of tGMR) - 30 into tLeft
if tXTicksVisible then
subtract the graphTickMajorWidth of me from tLeft
end if
add the graphYLabelXNudge of me to tLeft
put (item 2 of tGMR) - 6 into tBottom
add the graphYLabelYNudge of me to tBottom
makeAField "y varname", tGYL, "left", the graphXYLabelTextFont of me, "", "", tTS, tTH, "", tLeft, "", "", tBottom
end if
# 10. Key.
# 10a. Whether to create a key, and what its text will say.
put the graphYVariableNames of me into tKeyNames
put the graphYScalesInKey of me into tIncludeYScalesInKey
put the graphKeyLogIndicator of me into tLogIndicator
if tLogIndicator <> "" then put " " before tLogIndicator
put false into tMakeKey # Assume false until proven true.
put "" into tKeyContents
put 0 into i
repeat for each line tThisKeyName in tKeyNames
add 1 to i
if tThisKeyName <> "" then
put true into tMakeKey
put tThisKeyName after tKeyContents
if tYLogarithmic[i] then put tLogIndicator after tKeyContents
put line i of the graphYUnitsOfMeasureInKey of me into tUnitsOfMeasure
if tIncludeYScalesInKey then
if tUnitsOfMeasure <> "" then put " " before tUnitsOfMeasure
put " ("& displayRange(tYMin[i], tYMax[i]) & tUnitsOfMeasure &")" after tKeyContents # State the range and units of measure for this variable.
else if tUnitsOfMeasure <> "" then
put " ("& tUnitsOfMeasure &")" after tKeyContents # State the units of measure for this variable.
end if
put return after tKeyContents
end if
if i >= tNumCurves then exit repeat
end repeat
delete char -1 of tKeyContents # Delete trailing return.
# 10b. Make key.
if tMakeKey then
# 10b1. Make the text of the key.
put the graphKeyTextSize of me into tTS
put tTS + min(0, round(the graphKeyTextSeparation of me)) into tTH
put a + 20 + (the graphKeyXNudge of me) into tLeft
put tXLabelingBottom + 12 + (the graphKeyYNudge of me) into tTop
makeAField "key", tKeyContents, "left", the graphKeyTextFont of me, "plain", "", tTS, tTH, "", tLeft, tTop, "", ""
# 10b2. Plot line segments in the key.
repeat with i = 1 to tNumCurves
put "curve "& i into tCurveName
put the points of graphic tCurveName of me into tPoints
put tTop + roundUp(tTH/2) + (i-1)*tTH into tLabelLineY
put (tLeft - 20) &","& tLabelLineY into tPointA
put (tLeft - 5) &","& tLabelLineY into tPointB
put cr & cr & tPointA & cr & tPointB after tPoints
set the points of graphic tCurveName of me to tPoints
end repeat
end if
# 11. If requested, prepare for editable graph.
if (the graphEditable of me) and (tNumCurves > 0) then
reset templateButton
set the rect of the templateButton to tGraphCoverRect
set the script of the templateButton to "on mouseDown"& cr &" graphCoverClicked"& cr &"end mouseDown"
set the showName of the templateButton to false
set the showBorder of the templateButton to false
set the threeD of the templateButton to false
set the opaque of the templateButton to false
set the traversalOn of the templateButton to false
set the autoHilite of the templateButton to false
create button "graph cover" in me
set the cpEditCurveNum of button "graph cover" of me to tNumCurves
set the cpGraphYMin of button "graph cover" of me to tYMin[tNumCurves]
set the cpGraphYMax of button "graph cover" of me to tYMax[tNumCurves]
# A minor part of setting up is determining whether the x-data are ordered, because
# if the x-data are nondecreasing or nonincreasing, processing can be sped up for
# editing graphs.
put the points of graphic ("curve "& tNumCurves) of me into tPointsOfCurve
if tMakeKey then delete line -3 to -1 of tPointsOfCurve # Ignore parts that pertain to the key.
set the cpXDataRanges of button "graph cover" of me to clickXRanges(getXVals(tPointsOfCurve))
set the graphYDataEdited of me to tYData[tNumCurves]
else
set the graphYDataEdited of me to ""
end if
# 12. Unlock the screen and go back to the browse (hand) tool.
reset templateField
reset templateGraphic
reset templateButton
choose browse tool
unlock screen
end makeGraph
on noteDuplicatedPointNum pNewPointNum
put the number of items in aDuplicatedPointNums into tN
repeat with i = 1 to tN
put item i of aDuplicatedPointNums into tPN
if pNewPointNum < tPN then put (tPN+1) into item i of aDuplicatedPointNums
end repeat
put pNewPointNum into item (tN+1) of aDuplicatedPointNums
sort items of aDuplicatedPointNums numeric descending
end noteDuplicatedPointNum
# The following routine creates an axis-label field containing string s. The location of the
# field is relative to point pXLoc,pYLoc - which is normally the bottom (for x-ticks) or
# left (for y-ticks) point in an axis tick mark. pXOrY is either "x" or "y". The optional
# parameter tYColorsForScaleLabel can have color indications in different lines,
# to set the colors of different lines s. A multi-line s only makes sense for y-axis scales.
on makeAxisLabel pXOrY, pXLoc, pYLoc, s, pTextColors
if pXOrY = "x" and (the graphXScaleVisible of me = "false") then exit makeAxisLabel
if pXOrY = "y" and (the graphYScaleVisible of me = "false") then exit makeAxisLabel
add 1 to aNumScaleLabelsCreated
put "sl"& aNumScaleLabelsCreated into tFieldName
if pXOrY = "x" then put "center" into tTA else put "right" into tTA
put the graphScaleTextSize of me into tTS
if tTS = "" then put 9 into tTS
put tTS + min(0, round(the graphScaleTextSeparation of me)) into tTH
if pXOrY = "x" then
put 1 into tXFudge
put 1 into tYFudge
put round(pXLoc + tXFudge) into pXLocToUse
put "" into pRightToUse
put round(pYLoc + tYFudge) into pTopToUse
else
put 5 into tXFudge
put -1 into tYFudge
put "" into pXLocToUse
put round(pXLoc + tXFudge) into pRightToUse
put round(pYLoc + tYFudge - tTS/2) into pTopToUse
end if
put makeNumbersNiceForDisplay(s) into s
makeAField tFieldName, s, tTA, the graphScaleTextFont of me, "", pTextColors, tTS, tTH, (pXLocToUse &",0"), "", pTopToUse, pRightToUse, ""
if pXOrY = "x" then put the bottom of field tFieldName of me into aXScaleTextBottom
end makeAxisLabel
# Retun the passed string, ensuring that if it is a number -- or a series of numbers on separate
# lines -- the number(s) display nicely.
# A disadvantage of how I use this above is, I ought to give enough accuracy to display even
# a tiny range between min & max scales.
function makeNumbersNiceForDisplay pS
put the graphScaleExponentHighThreshold of me into tLargeNumberToExpThreshold
put the graphScaleExponentLowThreshold of me into tSmallNumberToExpThreshold
put the graphScaleMinimumSignificantDigits of me into tMinimumSignificantDigits
put the number of lines in pS into tNumLines
repeat with i = 1 to tNumLines
put line i of pS into s
if s is a number then
put s+0 into n
if n = 0 then
put "0" into s
else if abs(n) < tSmallNumberToExpThreshold or abs(n) >= tLargeNumberToExpThreshold then
put getMagnitude(n) into m
if the graphScaleExponentFormat of me is "^" then
put "*10^" into tExponentSeparator
else
put "e" into tExponentSeparator
end if
put round(n / 10^m, tMinimumSignificantDigits - 1) & tExponentSeparator & m into s
#put format("%3.2g", n / 10^m) & tExponentSeparator & m into s
else if n is an integer then
put n into s
else
put getMagnitude(n) into m
put min(0, m - (tMinimumSignificantDigits - 1)) into magnitudeAtWhichToRound
put round(n, -magnitudeAtWhichToRound) into s
#put format("%3.2g", n) into s
end if
end if
put s into line i of pS
end repeat
return pS
end makeNumbersNiceForDisplay
# The following routine creates a field as specified. Parameter pFieldName must be unique
# on each call. Parameters pTextSize and pTextHeight must be valid positive integers. To
# set the location of the field, either pass the location in pLoc, or pass the horizontal location
# in one of pLoc (the vertical location in pLoc is arbitrary) / pLeft / pRight and the vertical
# location in one of pLoc (the horizontal location in pLoc is arbitrary) / pTop / pBottom.
on makeAField pFieldName, pContents, pTextAlign, pTextFont, pTextStyle, pTextColors, pTextSize, pTextHeight, pLoc, pLeft, pTop, pRight, pBottom
reset templateField
set the threeD of the templateField to false
set the showBorder of the templateField to false
set the opaque of the templateField to false
set the lockText of the templateField to true
if pTextAlign <> "" then set the textAlign of the templateField to pTextAlign
if pTextFont <> "" then set the textFont of the templateField to pTextFont
set the textSize of the templateField to pTextSize # The textSize must be set after the textFont.
set the textHeight of the templateField to pTextHeight
if pTextStyle <> "" then set the textStyle of the templateField to pTextStyle
put the number of lines in pContents into tNumLines
put 10000 into h # Take a purposely too high guess at the necessary height to display the string.
#put tNumLines * pTextHeight + 8 into h
set the height of the templateField to h
put 10000 into w # Take a purposely too high guess at the necessary width to display the string.
# put maxLineLength(pContents) * pTextSize into w
# if pTextStyle contains "bold" then multiply w by 2
set the width of the templateField to w
set the autoTab of the templateField to false
create field pFieldName in me
put pContents into field pFieldName of me
put the formattedHeight of field pFieldName of me into h
set the height of field pFieldName of me to h
put (the formattedWidth of field pFieldName of me) + 10 into w # The formattedWidth is actually not wide enough to deter word wrapping (perhaps because of margins?), so I add 10.
set the width of field pFieldName of me to w
if pLoc <> "" then set the loc of field pFieldName of me to pLoc
if pLeft <> "" then set the left of field pFieldName of me to pLeft
if pTop <> "" then set the top of field pFieldName of me to pTop
if pRight <> "" then set the right of field pFieldName of me to pRight
if pBottom <> "" then set the bottom of field pFieldName of me to pBottom
if pTextColors <> "" then
put the number of lines in pTextColors into n
repeat with i = 1 to n
set the textColor of line i of field pFieldName of me to line i of pTextColors
end repeat
end if
end makeAField
function maxLineLength pString
put 0 into tMaxSoFar
repeat for each line l in pString
put length(l) into tLineLength
if tLineLength > tMaxSoFar then put tLineLength into tMaxSoFar
end repeat
return tMaxSoFar
end maxLineLength
function nonBlankItems s
put "" into r
repeat for each item thisItem in s
if thisItem <> "" then put thisItem &"," after r
end repeat
delete char -1 of r
return r
end nonBlankItems
function graphMarkerLineToPoints s
put word 1 of s into w1
if w1 = "" then
put false into tFilled
put "dot" into s
else if w1 = "none" then
return "" # No markers.
exit graphMarkerLineToPoints
else if w1 = "filled" or w1 = "solid" then
put true into tFilled
delete word 1 of s
else if w1 = "empty" or w1 = "hollow" then
put false into tFilled
delete word 1 of s
else #Default is hollow.
put false into tFilled
end if
put word 1 of s into tSizeWord
put word 2 of s into tTypeWord
if tTypeWord = "" then
put tSizeWord into tTypeWord
put "small" into tSizeWord
end if
set the wholeMatches to true
put wordOffset(tSizeWord, "tiny small