big steppy
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

1890 lines
52 KiB

  1. 'use strict';
  2. var things =
  3. {
  4. "Container": {
  5. "Container": Container,
  6. mass: 0,
  7. area: 0,
  8. clusters: 0,
  9. cluster_chances: 0,
  10. contents: [],
  11. descriptor: ["", ""]
  12. },
  13. //Creatures
  14. "Person": {
  15. "Person": Person,
  16. mass: 80,
  17. area: .33,
  18. clusters: 5,
  19. cluster_chances: .8,
  20. contents: [],
  21. descriptor: ["a person", "people"]
  22. },
  23. "Human": {
  24. "Human": Human,
  25. mass: 80,
  26. area: .33,
  27. clusters: 5,
  28. cluster_chances: .8,
  29. contents: [],
  30. descriptor: ["a person", "people"]
  31. },
  32. "Cow": {
  33. "Cow": Cow,
  34. mass: 300,
  35. area: 2,
  36. clusters: 15,
  37. cluster_chances: .5,
  38. contents: [],
  39. descriptor: ["a cow", "cattle"]
  40. },
  41. "Micro": {
  42. "Micro": Micro,
  43. mass: .01,
  44. area: .05,
  45. clusters: 50,
  46. cluster_chances: 1,
  47. contents: [],
  48. descriptor: ["a micro", "micros"]
  49. },
  50. "Macro": {
  51. "Macro": Macro,
  52. mass: 8e4,
  53. area: 100,
  54. clusters: 0,
  55. cluster_chances: 0,
  56. contents: [],
  57. descriptor: ["a smaller macro", "smaller macros"]
  58. },
  59. //Vehicles
  60. "Empty Car": {
  61. "Empty Car": EmptyCar,
  62. mass: 1000,
  63. area: 4,
  64. clusters: 2,
  65. cluster_chances: .3,
  66. contents: [],
  67. descriptor: ["a parked car", "parked cars"]
  68. },
  69. "Car": {
  70. "Car": Car,
  71. mass: 1000,
  72. area: 4,
  73. clusters: 4,
  74. cluster_chances: .5,
  75. contents: [["Person", 1, 4]],
  76. descriptor: ["a car", "cars"]
  77. },
  78. "Bus": {
  79. "Bus": Bus,
  80. mass: 5000,
  81. area: 12,
  82. clusters: 1,
  83. cluster_chances: .25,
  84. contents: [["Person", 2, 30]],
  85. descriptor: ["a bus", "busses"]
  86. },
  87. "Tram": {
  88. "Tram": Tram,
  89. mass: 1e4,
  90. area: 20,
  91. clusters: 1,
  92. cluster_chances: .2,
  93. contents: [["Person", 10, 50]],
  94. descriptor: ["a tram", "trams"]
  95. },
  96. "Train": {
  97. "Train": Train,
  98. mass: 5e4,
  99. area: 40,
  100. clusters: 2,
  101. cluster_chances: .1,
  102. contents: [["Person", 1, 4, "engine"], ["Train Car", 2, 10]],
  103. descriptor: ["a train", "trains"]
  104. },
  105. "Train Car": {
  106. "Train Car": TrainCar,
  107. mass: 7500,
  108. area: 20,
  109. clusters: 1,
  110. cluster_chances: .05,
  111. contents: [["Person", 10, 40]],
  112. descriptor: ["a train car", "train cars"]
  113. },
  114. "Helicopter": {
  115. "Helicopter": Helicopter,
  116. mass: 1500,
  117. area: 12,
  118. clusters: 0,
  119. cluster_chances: 0,
  120. contents: [["Person", 4, 16]],
  121. descriptor: ["a helicopter", "helicopters"]
  122. },
  123. "Empty Helicopter": {
  124. "Empty Helicopter": EmptyHelicopter,
  125. mass: 1500,
  126. area: 12,
  127. clusters: 3,
  128. cluster_chances: 0.05,
  129. contents: [],
  130. descriptor: ["a parked helicopter", "parked helicopters"]
  131. },
  132. "Plane": {
  133. "Plane": Plane,
  134. mass: 6500,
  135. area: 50,
  136. clusters: 1,
  137. cluster_chances: .05,
  138. contents: [],
  139. descriptor: ["a small plane", "small planes"]
  140. },
  141. "Empty Plane": {
  142. "Empty Plane": EmptyPlane,
  143. mass: 6500,
  144. area: 50,
  145. clusters: 1,
  146. cluster_chances: .05,
  147. contents: [["Person", 2, 9]],
  148. descriptor: ["a parked plane", "parked aircraft"]
  149. },
  150. "Airliner": {
  151. "Airliner": Airliner,
  152. mass: 6500,
  153. area: 1250,
  154. clusters: 1,
  155. cluster_chances: .05,
  156. contents: [["Person", 5, 300]],
  157. descriptor: ["an airliner", "airliners"]
  158. },
  159. "Empty Airliner": {
  160. "Empty Airliner": EmptyAirliner,
  161. mass: 6500,
  162. area: 1250,
  163. clusters: 1,
  164. cluster_chances: .05,
  165. contents: [],
  166. descriptor: ["a parked airliner", "parked airliners"]
  167. },
  168. //Buildings
  169. "House": {
  170. "House": House,
  171. mass: 1e4,
  172. area: 150,
  173. clusters: 5,
  174. cluster_chances: .5,
  175. contents: [["Person", 0, 8], ["Empty Car", 0, 2]],
  176. descriptor: ["a house", "houses"]
  177. },
  178. "Business": {
  179. "Business": Business,
  180. mass: 5e4,
  181. area: 400,
  182. clusters: 5,
  183. cluster_chances: .25,
  184. contents: [["Person", 0, 30], ["Car", 0, 5], ["Empty Car", 0, 20]],
  185. descriptor: ["a local business", "buildings"]
  186. },
  187. "Barn": {
  188. "Barn": Barn,
  189. mass: 5e3,
  190. area: 300,
  191. clusters: 1,
  192. cluster_chances: .1,
  193. contents: [["Person", 0, 2], ["Cow", 30, 70]],
  194. descriptor: ["a barn", "barns"]
  195. },
  196. "Small Hangar": {
  197. "Small Hangar": SmallHangar,
  198. mass: 5e5,
  199. area: 2500,
  200. clusters: 1,
  201. cluster_chances: .1,
  202. contents: [["Person", 0, 3], ["Plane", 0, 1], ["Empty Plane", 2, 6]],
  203. descriptor: ["a small hangar", "small hangars"]
  204. },
  205. "Helicopter Hangar": {
  206. "Helicopter Hangar": HelicopterHangar,
  207. mass: 5e5,
  208. area: 2000,
  209. clusters: 1,
  210. cluster_chances: .1,
  211. contents: [["Person", 0, 3], ["Helicopter", 0, 1], ["Helicopter", 2, 6]],
  212. descriptor: ["a helicopter hangar", "helicopter hangar"]
  213. },
  214. "Large Hangar": {
  215. "Large Hangar": LargeHangar,
  216. mass: 5e6,
  217. area: 8000,
  218. clusters: 1,
  219. cluster_chances: .1,
  220. contents: [["Person", 0, 5], ["Airliner", 0, 1], ["Empty Airliner", 1, 2]],
  221. descriptor: ["an aircraft hangar", "hangars"]
  222. },
  223. "Small Skyscraper": {
  224. "Small Skyscraper": SmallSkyscraper,
  225. mass: 1e7,
  226. area: 1000,
  227. clusters: 2,
  228. cluster_chances: .25,
  229. contents: [["Person", 150, 750], ["Empty Car", 10, 50]],
  230. descriptor: ["a small skyscraper", "small skyscrapers"]
  231. },
  232. "Large Skyscraper": {
  233. "Large Skyscraper": LargeSkyscraper,
  234. mass: 8e7,
  235. area: 2000,
  236. clusters: 1,
  237. cluster_chances: .25,
  238. contents: [["Person", 500, 1500], ["Empty Car", 20, 100]],
  239. descriptor: ["a large skyscraper", "large skyscrapers"]
  240. },
  241. "Parking Garage": {
  242. "Parking Garage": ParkingGarage,
  243. mass: 1e7,
  244. area: 750,
  245. clusters: 1,
  246. cluster_chances: .1,
  247. contents: [["Person", 10, 200], ["Empty Car", 100, 300], ["Car", 5, 30]],
  248. descriptor: ["a parking garage", "parking garages"]
  249. },
  250. //Places
  251. "Ranch": {
  252. "Ranch": Ranch,
  253. mass: 2e7,
  254. area: 4e4,
  255. clusters: 0,
  256. cluster_chances: 0,
  257. contents: [["Person", 10, 50], ["House", 1, 3], ["Barn", 1, 2]],
  258. descriptor: ["a ranch", "ranchs"]
  259. },
  260. "Airstrip": {
  261. "Airstrip": Airstrip,
  262. mass: 2e7,
  263. area: 9e5,
  264. clusters: 0,
  265. cluster_chances: 0,
  266. contents: [["Person", 10, 50], ["Small Hangar", 1, 3], ["Plane", 0, 2], ["Helicopter", 0, 1], ["Helicopter Hangar", 0, 1], ["Car", 0, 5], ["Empty Car", 0, 20]],
  267. descriptor: ["an airstrip", "airstrips"]
  268. },
  269. "Airport": {
  270. "Airport": Airport,
  271. mass: 1.5e8,
  272. area: 6e6,
  273. clusters: 0,
  274. cluster_chances: 0,
  275. contents: [["Person", 1500, 4000], ["Small Hangar", 4, 12], ["Plane", 2, 5], ["Helicopter", 1, 3], ["Helicopter Hangar", 2, 6], ["Airliner", 1, 3], ["Large Hangar", 2, 6], ["Car", 20, 75], ["Empty Car", 400, 1000]],
  276. descriptor: ["an airport", "airports"]
  277. },
  278. "Town": {
  279. "Town": Town,
  280. mass: 1,
  281. area: 1e7,
  282. clusters: 5,
  283. cluster_chances: .1,
  284. contents: [["Person", 10000, 100000], ["House", 5000, 50000], ["Empty Car", 200, 800], ["Car", 500, 80000], ["Bus", 5, 25], ["Train", 5, 25], ["Business", 500, 5000]],
  285. descriptor: ["a town", "towns"]
  286. },
  287. "City": {
  288. "City": City,
  289. mass: 1,
  290. area: 1e9,
  291. clusters: 0,
  292. cluster_chances: .2,
  293. contents: [["Person", 100000, 1500000], ["House", 20000, 200000], ["Empty Car", 10000, 100000], ["Car", 7500, 125000], ["Bus", 200, 400], ["Train", 10, 50], ["Tram", 25, 100], ["Small Skyscraper", 50, 300], ["Large Skyscraper", 10, 75], ["Parking Garage", 5, 10], ["Business", 2000, 10000]],
  294. descriptor: ["a city", "cities"]
  295. },
  296. "Continent": {
  297. "Continent": Continent,
  298. mass: 1e21,
  299. area: 1.5e13,
  300. clusters: 5,
  301. cluster_chances: .5,
  302. contents: [["Person", 1000000, 15000000], ["House", 2500, 10000], ["Car", 25000, 375000], ["Train", 50, 500], ["Town", 500, 1000], ["City", 50, 250], ["Business", 250, 1000]],
  303. descriptor: ["a continent", "continents"]
  304. },
  305. //Celestial Bodies
  306. "Planet": {
  307. "Planet": Planet,
  308. mass: 5.972e24,
  309. area: 2.5e14,
  310. clusters: 0,
  311. cluster_chances: 1,
  312. contents: [["Continent", 4, 9]],
  313. descriptor: ["a planet", "planets"]
  314. },
  315. "Star": {
  316. "Star": Star,
  317. mass: 1e40,
  318. area: 3e18,
  319. clusters: 1,
  320. cluster_chances: 1,
  321. contents: [],
  322. descriptor: ["a star", "stars"]
  323. },
  324. "Solar System": {
  325. "Solar System": SolarSystem,
  326. mass: 1,
  327. area: 3e21,
  328. clusters: 1,
  329. cluster_chances: 1,
  330. contents: [["Star", 1, 1], ["Planet", 5, 15]],
  331. descriptor: ["a solar system", "solar systems"]
  332. },
  333. "Galaxy": {
  334. "Galaxy": Galaxy,
  335. mass: 1,
  336. area: 2e45,
  337. clusters: 1,
  338. cluster_chances: 1,
  339. contents: [["Star", 1e9, 500e9], ["Solar System", 1e8, 500e8]],
  340. descriptor: ["a galaxy", "galaxies"]
  341. },
  342. "Cluster": {
  343. "Cluster": Cluster,
  344. mass: 1,
  345. area: 2e49,
  346. clusters: 1,
  347. cluster_chances: 1,
  348. contents: [["Galaxy", 200, 5000]],
  349. descriptor: ["a cluster", "clusters"]
  350. },
  351. "Universe": {
  352. "Universe": Universe,
  353. mass: 1,
  354. area: 7e53,
  355. clusters: 1,
  356. cluster_chances: 1,
  357. contents: [["Cluster", 1.5e9, 2.5e9]],
  358. descriptor: ["a universe", "universes"]
  359. },
  360. "Multiverse": {
  361. "Multiverse": Multiverse,
  362. mass: 1,
  363. area: 5e56,
  364. clusters: 1,
  365. cluster_chances: 1,
  366. contents: [["Universe", 100, 1000]],
  367. descriptor: ["a multiverse", "multiverses"]
  368. },
  369. "Timeline": {
  370. "Timeline": Timeline,
  371. mass: 1,
  372. area: 5e75,
  373. clusters: 1,
  374. cluster_chances: 1,
  375. contents: [["Multiverse", 1e50, 1e53]],
  376. descriptor: ["an entire timeline", "entire timelines"]
  377. },
  378. "Pantheon": {
  379. "Pantheon": Pantheon,
  380. mass: 1,
  381. area: 1e100,
  382. clusters: 1,
  383. cluster_chances: 1,
  384. contents: [["Timeline", 1e30, 1e35], ["Deity", 10, 30]],
  385. descriptor: ["a pantheon", "pantheons"]
  386. },
  387. "Deity": {
  388. "Deity": Deity,
  389. mass: 1e100,
  390. area: 1e100,
  391. clusters: 1,
  392. cluster_chances: 1,
  393. contents: [],
  394. descriptor: ["a deity", "deities"]
  395. },
  396. "Reality": {
  397. "Reality": Reality,
  398. mass: 1,
  399. area: 1e120,
  400. clusters: 1,
  401. cluster_changes: 1,
  402. contents: [["Pantheon", 1e30, 1e35]],
  403. descriptor: ["a reality", "realities"]
  404. },
  405. //Military
  406. "Soldier": {
  407. "Soldier": Soldier,
  408. mass: 80,
  409. area: 1,
  410. clusters: 2,
  411. cluster_chances: .2,
  412. contents: [],
  413. descriptor: ["a soldier", "soldiers"]
  414. },
  415. "Tank": {
  416. "Tank": Tank,
  417. mass: 5000,
  418. area: 20,
  419. clusters: 2,
  420. cluster_chances: .25,
  421. contents: [["Soldier", 3, 5]],
  422. descriptor: ["a tank", "tanks"]
  423. },
  424. "Artillery": {
  425. "Artillery": Artillery,
  426. mass: 7000,
  427. area: 25,
  428. clusters: 3,
  429. cluster_chances: .5,
  430. contents: [["Soldier", 4, 6]],
  431. descriptor: ["an artillery tank", "artillery tanks"]
  432. },
  433. "Military Helicopter": {
  434. "Military Helicopter": MilitaryHelicopter,
  435. mass: 1500,
  436. area: 12,
  437. clusters: 0,
  438. cluster_chances: 0,
  439. contents: [["Soldier", 4, 16]],
  440. descriptor: ["a helicopter", "helicopters"]
  441. },
  442. "Squad": {
  443. "Squad": Squad,
  444. mass: 1,
  445. area: 30,
  446. clusters: 20,
  447. cluster_chances: .05,
  448. contents: [["Soldier", 6, 9]],
  449. descriptor: ["a squad", "squads"]
  450. },
  451. "Platoon": {
  452. "Platoon": Platoon,
  453. mass: 100,
  454. area: 150,
  455. clusters: 2,
  456. cluster_chances: .1,
  457. contents: [["Soldier", 16, 44]],
  458. descriptor: ["a military platoon", "platoons"]
  459. },
  460. "Company": {
  461. "Company": Company,
  462. mass: 500,
  463. area: 600,
  464. clusters: 2,
  465. cluster_chances: .1,
  466. contents: [["Soldier", 60, 200]],
  467. descriptor: ["a company of soldiers", "companies"]
  468. },
  469. "Battalion": {
  470. "Battalion": Battalion,
  471. mass: 1000,
  472. area: 3500,
  473. clusters: 2,
  474. cluster_chances: .1,
  475. contents: [["Soldier", 300, 1000]],
  476. descriptor: ["a battalion", "battalions"]
  477. },
  478. "Brigade": {
  479. "Brigade": Brigade,
  480. mass: 1500,
  481. area: 2e4,
  482. clusters: 2,
  483. cluster_chances: .1,
  484. contents: [["Soldier", 1500, 3200]],
  485. descriptor: ["a brigade", "brigades"]
  486. },
  487. "Division": {
  488. "Division": Division,
  489. mass: 2000,
  490. area: 8e4,
  491. clusters: 3,
  492. cluster_chances: .1,
  493. contents: [["Soldier", 10000, 16000]],
  494. descriptor: ["a division", "divisions"]
  495. },
  496. "Tank Division": {
  497. "Tank Division": TankDivision,
  498. mass: 3000,
  499. area: 1e5,
  500. clusters: 1,
  501. cluster_chances: .15,
  502. contents: [["Soldier", 8000, 1200], ["Tank", 250, 500]],
  503. descriptor: ["a tank division", "tank divisions"]
  504. },
  505. "Army": {
  506. "Army": Army,
  507. mass: 5000,
  508. area: 1e6,
  509. clusters: 2,
  510. cluster_chances: .1,
  511. contents: [["Soldier", 40000, 75000]],
  512. descriptor: ["an army", "armies"]
  513. },
  514. };
  515. //Alterante Army Structuring, may be used later
  516. //"Squad": [["Soldier",6,9]],
  517. // "Platoon": [["Squad",3,4]],
  518. //"Company": [["Platoon",3,5],["Squad",0,2]],
  519. //"Battalion": [["Company",4,6]],
  520. //"Brigade": [["Battalion",2,5],["Company",0,3]],
  521. //"Division": [["Brigade",2,4]],
  522. //"Tank Division": [["Brigade",2,4],["Tank",250,500]],
  523. //"Army": [["Division",3,8],["Tank Division",1,5]],
  524. // replace all instances of from with to
  525. function contents_substitute(from, to) {
  526. for (let key in contents) {
  527. if (contents.hasOwnProperty(key)) {
  528. let type = contents[key];
  529. for (let i = 0; i < type.length; i++) {
  530. if (type[i][0] == from) {
  531. type[i][0] = to;
  532. }
  533. }
  534. }
  535. }
  536. }
  537. // remove all instances of thing
  538. function contents_remove(thing) {
  539. for (let key in contents) {
  540. if (contents.hasOwnProperty(key)) {
  541. let type = contents[key];
  542. for (let i = 0; i < type.length; i++) {
  543. if (type[i][0] == thing) {
  544. type.splice(i, 1);
  545. --i;
  546. }
  547. }
  548. }
  549. }
  550. }
  551. // adds thing to parent
  552. function contents_insert(parent, thing, min, max, label) {
  553. let owner = things[parent].contents;
  554. if (label == undefined)
  555. owner.push([thing, min, max]);
  556. else
  557. owner.push([thing, min, max, label]);
  558. }
  559. function initContents(name, count) { //builds the contents for each destrucable(thing) when called
  560. let result = {};
  561. let type = things[name].contents;
  562. for (let i = 0; i < type.length; i++) {
  563. let amount = distribution(type[i][1], type[i][2], count); //arrays of contents look like ["thing name",min,max,"optional name"] so those values have to pulled out
  564. if (amount > 0) {
  565. // if a custom label is supplied, use it!
  566. if (type[i].length == 4) //if has optional name
  567. result[type[i][3]] = new things[type[i][0]][type[i][0]](amount); //creates a "thing name" under the key of "optional name"
  568. else
  569. result[type[i][0]] = new things[type[i][0]][type[i][0]](amount);
  570. }
  571. }
  572. return result;
  573. }
  574. function get_living_prey(sum) {
  575. let total = 0;
  576. for (let key in sum) {
  577. if (sum.hasOwnProperty(key)) {
  578. if (key == "Micro" || key == "Macro" || key == "Person" || key == "Cow" || key == 'Soldier')
  579. total += sum[key];
  580. }
  581. }
  582. return total;
  583. }
  584. // general logic: each step fills in a fraction of the remaining space
  585. function fill_area(area, weights, variance = 0.15) {
  586. area = area + Math.random() * variance * 2 * area - variance * area;
  587. var result = [];
  588. var candidates = [];
  589. for (var key in weights) {
  590. if (weights.hasOwnProperty(key)) {
  591. candidates.push({ "name": key, "area": things[key].area, "weight": weights[key] });
  592. }
  593. }
  594. candidates = candidates.sort(function (x, y) {
  595. return x.area - y.area;
  596. });
  597. while (candidates.length > 0) {
  598. var candidate = candidates.pop();
  599. if (candidate.area > area)
  600. continue;
  601. var max = Math.floor(area / candidate.area);
  602. var limit = Math.min(max, 1000);
  603. var count = 0;
  604. var loopvar = 0;
  605. // for small amounts, actually do the randomness
  606. // the first few ones get a much better shot
  607. // if we have nothing at all, it's even better!
  608. while (loopvar < limit) {
  609. if (loopvar == 0 && result.length == 0) {
  610. ++count;
  611. }
  612. else if (loopvar <= things[candidate.name].clusters) {
  613. if (Math.random() < candidate.weight ? 1 : Math.random() < things[candidate.name].cluster_chances) {
  614. ++count;
  615. }
  616. }
  617. else {
  618. count += Math.random() < candidate.weight ? 1 : 0;
  619. }
  620. ++loopvar;
  621. }
  622. // if we're doing more than the limit, then we just add on the rest, with some variance
  623. if (limit < max) {
  624. const base = (max - limit) * candidate.weight;
  625. count += Math.round(base - base / 10 + base * Math.random() / 5);
  626. }
  627. area -= count * candidate.area;
  628. if (count > 0)
  629. result.push(new things[candidate.name][candidate.name](count));
  630. }
  631. return new Container(result);
  632. }
  633. // maybe make this something that approximates a
  634. // normal distribution; doing this 15,000,000 times is bad...
  635. // solution: only a few are random lul
  636. // improvement: take up to 100 samples, then use that to scale the final result
  637. function distribution(min, max, samples) {
  638. var result = 0;
  639. var limit = Math.min(100, samples);
  640. if (limit < samples) {
  641. let dist = 0;
  642. for (let i = 0; i < limit; i++) {
  643. dist += Math.random();
  644. }
  645. dist /= 100;
  646. return Math.floor(dist * samples * (max - min + 1) + samples * min);
  647. } else {
  648. for (let i = 0; i < limit; i++) {
  649. result += Math.floor(Math.random() * (max - min + 1) + min);
  650. }
  651. }
  652. return result;
  653. }
  654. function defaultMultiply(thing) {
  655. return function (amount) {
  656. thing.count *= amount;
  657. for (var key in thing.contents) {
  658. if (thing.contents.hasOwnProperty(key)) {
  659. thing.contents[key].multiply(amount);
  660. }
  661. }
  662. };
  663. }
  664. function defaultArea(thing) {
  665. return things[thing.name].area;
  666. }
  667. function defaultMass(thing) {
  668. return things[thing.name].mass;
  669. }
  670. function defaultDescribeOne(thing) {
  671. return function (verbose) { //verbose doesn't matter for this case, becasue it handles things with no extra text to use when being verbose
  672. return things[thing.name].descriptor[0];
  673. }
  674. }
  675. function defaultMerge(thing) { //this merges all objects into one containers
  676. return function (container) {
  677. var newCount = this.count + container.count;
  678. var newThing = new things[thing.name][thing.name](newCount);
  679. newThing.contents = {};
  680. for (var key in this.contents) {
  681. if (this.contents.hasOwnProperty(key)) {
  682. newThing.contents[key] = this.contents[key];
  683. }
  684. }
  685. for (key in container.contents) {
  686. if (container.contents.hasOwnProperty(key)) {
  687. if (this.contents.hasOwnProperty(key)) {
  688. newThing.contents[key] = this.contents[key].merge(container.contents[key]);
  689. } else {
  690. newThing.contents[key] = container.contents[key];
  691. }
  692. }
  693. }
  694. return newThing;
  695. };
  696. }
  697. function listSum(sum) {
  698. let result = [];
  699. for (let key in sum) {
  700. if (sum.hasOwnProperty(key)) {
  701. result.push(new things[key][key](sum[key]).describe(false));
  702. }
  703. }
  704. return merge_things(result);
  705. }
  706. // turn a nested object into a container with everything on one level
  707. function flatten(thing) {
  708. let dict = defaultSum(thing)();
  709. let list = [];
  710. Object.entries(dict).forEach(function ([key, val]) {
  711. let obj = new things[key][key](val);
  712. obj.contents = [];
  713. list.push(obj);
  714. });
  715. list.sort(function (x, y) {
  716. if (y.area != x.area) {
  717. return y.area - x.area;
  718. } else {
  719. return x.name.localeCompare(y.name);
  720. }
  721. });
  722. return new Container(list);
  723. }
  724. function defaultSum(thing) {
  725. return function () {
  726. var counts = {};
  727. if (thing.name != "Container")
  728. counts[thing.name] = thing.count;
  729. for (var key in thing.contents) {
  730. if (thing.contents.hasOwnProperty(key)) {
  731. var subcount = thing.contents[key].sum();
  732. for (var subkey in subcount) {
  733. if (!counts.hasOwnProperty(subkey)) {
  734. counts[subkey] = 0;
  735. }
  736. counts[subkey] += subcount[subkey];
  737. }
  738. }
  739. }
  740. return counts;
  741. };
  742. }
  743. function defaultSumProperty(thing) {
  744. return function (prop) {
  745. var total = 0;
  746. total += thing[prop] * thing.count;
  747. for (var key in thing.contents) {
  748. if (thing.contents.hasOwnProperty(key)) {
  749. total += thing.contents[key].sum_property(prop);
  750. }
  751. }
  752. return total;
  753. };
  754. }
  755. function defaultModProperty(thing) {
  756. return function(prop, func) {
  757. thing[prop] = func(thing[prop]);
  758. for (var key in thing.contents) {
  759. if (thing.contents.hasOwnProperty(key)) {
  760. thing.contents[key].mod_property(prop, func);
  761. }
  762. }
  763. };
  764. }
  765. function defaultAddContent(thing) {
  766. return function (name, min, max, count) {
  767. if (min == max) {
  768. let object = new things[name](min * count);
  769. thing.contents[object.name] = object;
  770. } else {
  771. let object = new things[name](distribution(min, max, count));
  772. thing.contents[object.name] = object;
  773. }
  774. };
  775. }
  776. function DefaultEntity() {
  777. this.sum = defaultSum;
  778. this.area = defaultArea;
  779. this.mass = defaultMass;
  780. this.sum_property = defaultSumProperty;
  781. this.mod_property = defaultModProperty;
  782. this.merge = defaultMerge;
  783. this.multiply = defaultMultiply;
  784. this.describeSimple = defaultDescribeSimple;
  785. this.describeOne = defaultDescribeOne;
  786. return this;
  787. }
  788. // god I love reinventing the wheel
  789. function copy_defaults(self, proto) { //loads the values defined in things into the fuction that calls it
  790. for (var key in proto) { //proto will always be a new DefaultEntity, self is the parent function
  791. if (proto.hasOwnProperty(key)) {
  792. self[key] = proto[key](self);
  793. }
  794. }
  795. }
  796. // combine strings into a list with proper grammar
  797. function merge_things(list, semicolons = false) {
  798. if (list.length == 0) {
  799. return "";
  800. } else if (list.length == 1) {
  801. return list[0];
  802. } else if (list.length == 2) {
  803. return list[0] + " and " + list[1];
  804. } else {
  805. var result = "";
  806. list.slice(0, list.length - 1).forEach(function (term) {
  807. result += term + ", ";
  808. });
  809. result += "and " + list[list.length - 1];
  810. return result;
  811. }
  812. }
  813. // combine the adjectives for something into a single string
  814. function merge_desc(list) {
  815. var result = "";
  816. list.forEach(function (term) {
  817. if (term != "")
  818. result += term + " ";
  819. });
  820. // knock off the last space
  821. if (result.length > 0) {
  822. result = result.substring(0, result.length - 1);
  823. }
  824. let article = "a "
  825. //a/an overwriting terms
  826. let forcedTerms = ["honor", "heir"]; //words that need to start with an but don't start with a,e,i,o,u
  827. let force = false;
  828. for (let i of forcedTerms) {
  829. if (i === result.substring(0, i.length)) { force = true; }
  830. }
  831. let exceptionTerms = ["uniform", "unique"]; //words that need to start with a and start with a,e,i,o,u
  832. let exception = false;
  833. for (let i of exceptionTerms) {
  834. if (i === result.substring(0, i.length)) { exception = true; }
  835. }
  836. //check if the string should start with an
  837. if ((force == true) || (exception == false && ((result.charAt(0) == "a") || (result.charAt(0) == "e") || (result.charAt(0) == "i") || (result.charAt(0) == "o") || (result.charAt(0) == "u")))) {
  838. article = "an ";
  839. }
  840. result = article + result;
  841. return result;
  842. }
  843. // describes everything in the container
  844. function describe_all(contents, verbose = true, except = []) {
  845. var things = [];
  846. for (var key in contents) {
  847. if (contents.hasOwnProperty(key) && !except.includes(key)) {
  848. things.push(contents[key].describe(verbose));
  849. }
  850. }
  851. return merge_things(things);
  852. }
  853. function random_desc(list, odds = 1) { //strings together an array into a series of words
  854. if (Math.random() < odds)
  855. return list[Math.floor(Math.random() * list.length)];
  856. else
  857. return "";
  858. }
  859. function defaultDescribeSimple(thing) {
  860. return function (flat) {
  861. if (flat) {
  862. return flatten(thing).describe(false)
  863. } else {
  864. return thing.describe(false);
  865. }
  866. }
  867. }
  868. function defaultDescribe(verbose = true, parent, descAs) {
  869. let descriptorEnd = " inside";
  870. let descriptorConjunction = " with ";
  871. let groupLessThan3 = false;
  872. switch (descAs) {
  873. case "vehicle":
  874. descriptorEnd = pickString(" inside", " inside", " inside", " inside", " riding inside", " trapped inside", " sitting inside");
  875. break;
  876. case "community":
  877. groupLessThan3 = true;
  878. descriptorEnd = " in " + (parent.count == 1 ? "it" : "them");
  879. break;
  880. case "celestial":
  881. groupLessThan3 = true;
  882. descriptorConjunction = pickString(" made up of ", " consisting of ", " containing ");
  883. descriptorEnd = "";
  884. break;
  885. case "military":
  886. groupLessThan3 = true;
  887. descriptorConjunction = pickString(" of ", " of ", " made up of ", " comprised of ", " containing ");
  888. descriptorEnd = "";
  889. break;
  890. case "generic vehicle":
  891. groupLessThan3 = true;
  892. descriptorEnd = pickString(" inside", " inside", " inside", " inside", " riding inside", " trapped inside", " sitting inside");
  893. break;
  894. } if (verbose) {
  895. if (parent.count == 1) { //singular parent (specifying single to catch cases where groupLessThan3 = true, otherwise it would output "1 towns" instead of "a town"
  896. if (things[parent.name].contents.length > 0) {
  897. return (things[parent.name].descriptor[0] + descriptorConjunction + describe_all(parent.contents, false) + descriptorEnd);
  898. } else {
  899. return parent.describeOne(verbose);
  900. }
  901. }
  902. else if (parent.count <= 3 && groupLessThan3 == false) { // less than 3 parents and an ojbect that has varety when described
  903. var list = [];
  904. for (var i = 0; i < parent.count; i++) {
  905. list.push(parent.describeOne(parent.count <= 2));
  906. }
  907. if (things[parent.name].contents.length > 0) {
  908. return (merge_things(list) + descriptorConjunction + describe_all(parent.contents, false) + descriptorEnd);
  909. } else {
  910. return merge_things(list);
  911. }
  912. } else {//if there are more than 3 of the object
  913. if (things[parent.name].contents.length > 0) {
  914. return (parent.count + " " + things[parent.name].descriptor[1] + descriptorConjunction + describe_all(parent.contents, false) + descriptorEnd);
  915. } else {
  916. return (parent.count + " " + things[parent.name].descriptor[1]);
  917. }
  918. }
  919. } else {//not verbose
  920. return (parent.count > 1 ? (parent.count + " " + things[parent.name].descriptor[1]) : things[parent.name].descriptor[0]);
  921. }
  922. }
  923. function Container(contents = []) {
  924. this.name = "Container";
  925. copy_defaults(this, new DefaultEntity());
  926. if (Number.isInteger(contents))
  927. this.count = contents;
  928. else
  929. this.count = 0;
  930. this.contents = {};
  931. for (var i = 0; i < contents.length; i++) {
  932. this.contents[contents[i].name] = contents[i];
  933. }
  934. for (var key in this.contents) {
  935. if (this.contents.hasOwnProperty(key)) {
  936. this.count += this.contents[key].count;
  937. }
  938. }
  939. this.describe = function (verbose = true) {
  940. return describe_all(this.contents, verbose);
  941. };
  942. return this;
  943. }
  944. function Person(count = 1) {
  945. this.name = "Person";
  946. copy_defaults(this, new DefaultEntity());
  947. this.mass = ((Math.random() - .5) * 20) + this.mass;
  948. this.count = count;
  949. this.contents = initContents(this.name, this.count);
  950. this.describeOne = function (verbose = true) {
  951. var body = random_desc(["skinny", "fat", "tall", "short", "stocky", "spindly", "muscular", "fit", "multi-colored"], (verbose ? 0.6 : 0));
  952. var sex = random_desc(["male", "female"], (verbose ? 0.75 : 0));
  953. var species = "";
  954. species = random_desc(["wolf", "cat", "dog", "squirrel", "horse", "hyena", "fox", "jackal", "crux", "sergal", "coyote", "rabbit", "lizard", "avian"]);
  955. return merge_desc([body, sex, species]);
  956. };
  957. this.describe = function (verbose = true) {
  958. return defaultDescribe(verbose, this);
  959. }
  960. return this;
  961. }
  962. function Human(count = 1) {
  963. this.name = "Person";
  964. copy_defaults(this, new DefaultEntity());
  965. this.mass = ((Math.random() - .5) * 20) + this.mass;
  966. this.count = count;
  967. this.contents = initContents(this.name, this.count);
  968. this.describeOne = function (verbose = true) {
  969. var body = random_desc(["skinny", "fat", "tall", "short", "stocky", "spindly", "muscular", "fit", "tanned"], (verbose ? 0.6 : 0));
  970. var sex = random_desc(["man", "woman"], 1);
  971. return merge_desc([body, sex]);
  972. };
  973. this.describe = function (verbose = true) {
  974. return defaultDescribe(verbose, this);
  975. }
  976. return this;
  977. }
  978. function Cow(count = 1) {
  979. this.name = "Cow";
  980. copy_defaults(this, new DefaultEntity());
  981. this.count = count;
  982. this.contents = initContents(this.name, this.count);
  983. this.describeOne = function (verbose = true) {
  984. var body = random_desc(["skinny", "fat", "tall", "short", "stocky", "spindly", "brown"], (verbose ? 0.6 : 0));
  985. var sex = random_desc(["bull", "steer", "cow", "cow", "cow", "heifer"], (verbose ? 1 : 0));
  986. return merge_desc([body, sex]);
  987. };
  988. this.describe = function (verbose = true) {
  989. return defaultDescribe(verbose, this);
  990. }
  991. return this;
  992. }
  993. function EmptyCar(count = 1) {
  994. this.name = "Empty Car";
  995. copy_defaults(this, new DefaultEntity());
  996. this.count = count;
  997. this.contents = initContents(this.name, this.count);
  998. this.describeOne = function (verbose = true) {
  999. var color = random_desc(["black", "black", "gray", "gray", "blue", "red", "tan", "white", "white"]);
  1000. var adjective = random_desc(["rusty", "brand-new", "luxury", "beat-up", "dented", "restored", "classic"], 0.3);
  1001. var type = random_desc(["SUV", "coupe", "sedan", "truck", "van", "convertible"]);
  1002. return merge_desc(["parked", adjective, color, type]);
  1003. };
  1004. this.describe = function (verbose = true) {
  1005. return defaultDescribe(verbose, this, "vehicle");
  1006. }
  1007. }
  1008. function Car(count = 1) {
  1009. this.name = "Car";
  1010. copy_defaults(this, new DefaultEntity());
  1011. this.count = count;
  1012. this.contents = initContents(this.name, this.count);
  1013. this.describeOne = function (verbose = true) {
  1014. var color = random_desc(["black", "black", "gray", "gray", "blue", "red", "tan", "white", "white"], (verbose ? 1 : 0));
  1015. var adjective = random_desc(["rusty", "brand-new", "luxury", "beat-up", "dented", "restored", "classic"], (verbose ? 0.3 : 0));
  1016. var type = random_desc(["SUV", "coupe", "sedan", "truck", "van", "convertible"]);
  1017. return merge_desc([adjective, color, type]);
  1018. };
  1019. this.describe = function (verbose = true) {
  1020. return defaultDescribe(verbose, this, "vehicle");
  1021. }
  1022. }
  1023. function Bus(count = 1) {
  1024. this.name = "Bus";
  1025. copy_defaults(this, new DefaultEntity());
  1026. this.count = count;
  1027. this.contents = initContents(this.name, this.count);
  1028. this.describeOne = function (verbose = true) {
  1029. var adjective = random_desc(["rusty", "brand-new", "aging", "modern"], (verbose ? 0.3 : 0));
  1030. var color = random_desc(["black", "tan", "gray"], (verbose ? 1 : 0));
  1031. var type = random_desc(["bus", "double-decker bus", "articulating bus", "open-top bus", "sleeper bus", "intercity bus"]);
  1032. return merge_desc([adjective, color, type]);
  1033. };
  1034. this.describe = function (verbose = true) {
  1035. return defaultDescribe(verbose, this, "vehicle");
  1036. }
  1037. }
  1038. function Tram(count = 1) {
  1039. this.name = "Tram";
  1040. copy_defaults(this, new DefaultEntity());
  1041. this.count = count;
  1042. this.contents = initContents(this.name, this.count);
  1043. this.describeOne = function (verbose = true) {
  1044. var adjective = random_desc(["rusty", "weathered", "well-maintained",], (verbose ? 0.3 : 0));
  1045. var color = random_desc(["blue", "brown", "gray"], (verbose ? 1 : 0));
  1046. var type = random_desc(["tram"]);
  1047. return merge_desc([adjective, color, type]);
  1048. };
  1049. this.describe = function (verbose = true) {
  1050. return defaultDescribe(verbose, this, "vehicle");
  1051. }
  1052. this.anal_vore = function () {
  1053. return "You slide " + this.describe() + " up your tight ass";
  1054. };
  1055. }
  1056. function EmptyHelicopter(count = 1) {
  1057. this.name = "Empty Helicopter";
  1058. copy_defaults(this, new DefaultEntity());
  1059. this.count = count;
  1060. this.contents = initContents(this.name, this.count);
  1061. this.describeOne = function (verbose = true) {
  1062. var color = random_desc(["blue", "white", "white", "red", "black", "gold", "yellow"], (verbose ? 0.6 : 0));
  1063. var type = random_desc(["bubble coptor", "helicopter", "helicopter", "news chopper", "police helicopter", "chopper"]);
  1064. return merge_desc([adjective, color, type]);
  1065. };
  1066. this.describe = function (verbose = true) {
  1067. return defaultDescribe(verbose, this, "vehicle");
  1068. }
  1069. }
  1070. function Helicopter(count = 1) {
  1071. this.name = "Helicopter";
  1072. copy_defaults(this, new DefaultEntity());
  1073. this.count = count;
  1074. this.contents = initContents(this.name, this.count);
  1075. this.describeOne = function (verbose = true) {
  1076. var color = random_desc(["blue", "white", "white", "red", "black", "gold", "yellow"], (verbose ? 0.6 : 0));
  1077. var type = random_desc(["bubble coptor", "helicopter", "helicopter", "news chopper", "police helicopter", "chopper"]);
  1078. return merge_desc([adjective, color, type]);
  1079. };
  1080. this.describe = function (verbose = true) {
  1081. return defaultDescribe(verbose, this, "vehicle");
  1082. }
  1083. }
  1084. function EmptyPlane(count = 1) {
  1085. this.name = "Empty Plane";
  1086. copy_defaults(this, new DefaultEntity());
  1087. this.count = count;
  1088. this.contents = initContents(this.name, this.count);
  1089. this.describeOne = function (verbose = true) {
  1090. var adjective = random_desc(["brand-new", "aging", "modern"], (verbose ? 0.2 : 0));
  1091. var color = random_desc(["blue", "white", "white", "blue and white", "red and white", "black", "gold"], (verbose ? 0.9 : 0));
  1092. var type = random_desc(["luxury jet", "business jet", "single-engine plane", "light aircraft"]);
  1093. return merge_desc([adjective, color, type]);
  1094. };
  1095. this.describe = function (verbose = true) {
  1096. return defaultDescribe(verbose, this, "vehicle");
  1097. }
  1098. }
  1099. function Plane(count = 1) {
  1100. this.name = "Plane";
  1101. copy_defaults(this, new DefaultEntity());
  1102. this.count = count;
  1103. this.contents = initContents(this.name, this.count);
  1104. this.describeOne = function (verbose = true) {
  1105. var adjective = random_desc(["brand-new", "aging", "modern"], (verbose ? 0.2 : 0));
  1106. var color = random_desc(["blue", "white", "white", "blue and white", "red and white", "black", "gold"], (verbose ? 0.9 : 0));
  1107. var type = random_desc(["luxury jet", "business jet", "single-engine plane", "light aircraft"]);
  1108. return merge_desc([adjective, color, type]);
  1109. };
  1110. this.describe = function (verbose = true) {
  1111. return defaultDescribe(verbose, this, "vehicle");
  1112. }
  1113. }
  1114. function EmptyAirliner(count = 1) {
  1115. this.name = "Empty Airliner";
  1116. copy_defaults(this, new DefaultEntity());
  1117. this.count = count;
  1118. this.contents = initContents(this.name, this.count);
  1119. this.describeOne = function (verbose = true) {
  1120. var adjective = random_desc(["brand-new", "aging", "modern"], (verbose ? 0.2 : 0));
  1121. var color = random_desc(["blue", "white", "white", "blue and white"], (verbose ? 0.9 : 0));
  1122. var type = random_desc(["airliner", "twin-engine jet", "trijet", "four engine jet", "double-decker airliner", "widebody airliner", "passenger jet", "airliner"]);
  1123. return merge_desc([adjective, color, type]);
  1124. };
  1125. this.describe = function (verbose = true) {
  1126. return defaultDescribe(verbose, this, "vehicle");
  1127. }
  1128. }
  1129. function Airliner(count = 1) {
  1130. this.name = "Airliner";
  1131. copy_defaults(this, new DefaultEntity());
  1132. this.count = count;
  1133. this.contents = initContents(this.name, this.count);
  1134. this.describeOne = function (verbose = true) {
  1135. var adjective = random_desc(["brand-new", "aging", "modern"], (verbose ? 0.2 : 0));
  1136. var color = random_desc(["blue", "white", "white", "blue and white"], (verbose ? 0.9 : 0));
  1137. var type = random_desc(["airliner", "twin-engine jet", "trijet", "four engine jet", "double-decker airliner", "widebody airliner", "passenger jet", "airliner"]);
  1138. return merge_desc([adjective, color, type]);
  1139. };
  1140. this.describe = function (verbose = true) {
  1141. return defaultDescribe(verbose, this, "vehicle");
  1142. }
  1143. }
  1144. function Train(count = 1) {
  1145. this.name = "Train";
  1146. copy_defaults(this, new DefaultEntity());
  1147. this.count = count;
  1148. this.contents = initContents(this.name, this.count);
  1149. this.describeOne = function (verbose = true) {
  1150. var adjective = random_desc(["rusty", "brand-new", "steam", "freshly-painted"], (verbose ? 0.3 : 0));
  1151. var color = random_desc(["black", "tan", "gray"], (verbose ? 1 : 0));
  1152. var type = random_desc(["train", "passenger train", "freight train"]);
  1153. return merge_desc([adjective, color, type]);
  1154. };
  1155. this.describe = function (verbose = true) {
  1156. if (verbose) {
  1157. if (this.count == 1) {
  1158. var list = [];
  1159. for (var i = 0; i < this.count; i++) {
  1160. list.push(this.describeOne(verbose));
  1161. }
  1162. return merge_things(list) + " with " + this.contents["engine"].describe(false) + " in the engine and " + this.contents["Train Car"].describe() + " attached";
  1163. } else {
  1164. return this.count + " trains with " + this.contents["engine"].describe(false) + " in the engine and " + this.contents["Train Car"].describe() + " attached";
  1165. }
  1166. } else {
  1167. return (this.count > 1 ? this.count + " trains" : "a train");
  1168. }
  1169. };
  1170. this.anal_vore = function () {
  1171. var cars = (this.contents["Train Car"].count == 1 ? this.contents["Train Car"].describe() + " follows it inside" : this.contents["Train Car"].describe() + " are pulled slowly inside");
  1172. return "You snatch up " + this.describeOne() + " and stuff it into your pucker, moaning as " + cars;
  1173. };
  1174. }
  1175. function TrainCar(count = 1) {
  1176. this.name = "Train Car";
  1177. copy_defaults(this, new DefaultEntity());
  1178. this.count = count;
  1179. this.contents = initContents(this.name, this.count);
  1180. this.describeOne = function (verbose = true) {
  1181. var adjective = random_desc(["rusty", "brand-new", "vintage", "graffitied", "well-maintained"], (verbose ? 0.3 : 0));
  1182. var color = random_desc(["black", "tan", "gray", "yellow", "steel", "wooden"], (verbose ? 1 : 0));
  1183. var type = random_desc(["train car", "passenger train car", "freight train car"]);
  1184. return merge_desc([adjective, color, type]);
  1185. };
  1186. this.describe = function (verbose = true) {
  1187. return defaultDescribe(verbose, this, "vehicle");
  1188. }
  1189. }
  1190. function House(count = 1) {
  1191. this.name = "House";
  1192. copy_defaults(this, new DefaultEntity());
  1193. this.count = count;
  1194. this.contents = initContents(this.name, this.count);
  1195. this.describeOne = function (verbose = true) {
  1196. var size = random_desc(["little", "two-story", "large", "well-built", "run-down", "cheap",], (verbose ? 0.5 : 0));
  1197. var color = random_desc(["blue", "white", "gray", "tan", "green", "wooden", "brick"], (verbose ? 0.5 : 0));
  1198. var name = random_desc(["house", "home", "duplex", "house", "house", "trailer"], 1);
  1199. return merge_desc([size, color, name]);
  1200. };
  1201. this.describe = function (verbose = true) {
  1202. return defaultDescribe(verbose, this);
  1203. }
  1204. }
  1205. //might split this into a general business and resutrant categories
  1206. function Business(count = 1) {
  1207. this.name = "Business";
  1208. copy_defaults(this, new DefaultEntity());
  1209. this.count = count;
  1210. this.contents = initContents(this.name, this.count);
  1211. this.describeOne = function (verbose = true) {
  1212. var size = random_desc(["little", "two-story", "large", "well-built", "run-down", "cheap", "aging", "corner"], (verbose ? 0.5 : 0));
  1213. var color = random_desc(["blue", "white", "gray", "tan", "green", "brick", "concrete"], (verbose ? 0.5 : 0));
  1214. var name = random_desc(["mall", "resturant", "bank", "clinic", "shop", "post office", "tire shop", "chain resturant", "grocery store", "barber shop", "pizza resturant", "hardware store", "movie theather", "gas station"], 1);
  1215. return merge_desc([size, color, name]);
  1216. };
  1217. this.describe = function (verbose = true) {
  1218. return defaultDescribe(verbose, this);
  1219. }
  1220. }
  1221. function Barn(count = 1) {
  1222. this.name = "Barn";
  1223. copy_defaults(this, new DefaultEntity());
  1224. this.count = count;
  1225. this.contents = initContents(this.name, this.count);
  1226. this.describeOne = function (verbose = true) {
  1227. var size = random_desc(["little", "big", "large", "weathered", "rotted", "new"], (verbose ? 0.5 : 0));
  1228. var color = random_desc(["blue", "white", "gray", "tan", "green", "red"], (verbose ? 0.5 : 0));
  1229. var name = random_desc(["barn", "barn", "barn", "barn", "barn", "farmhouse"], 1);
  1230. return merge_desc([size, color, name]);
  1231. };
  1232. this.describe = function (verbose = true) {
  1233. return defaultDescribe(verbose, this);
  1234. }
  1235. }
  1236. function SmallHangar(count = 1) {
  1237. this.name = "Small Hangar";
  1238. copy_defaults(this, new DefaultEntity());
  1239. this.count = count;
  1240. this.contents = initContents(this.name, this.count);
  1241. this.describeOne = function (verbose = true) {
  1242. var size = random_desc(["weathered", "aging", "new"], (verbose ? 0.5 : 0));
  1243. var color = random_desc(["blue", "white", "gray", "tan", "green"], (verbose ? 0.5 : 0));
  1244. var name = random_desc(["hangar", "hangar", "hangar", "aircraft hangar"], 1);
  1245. return merge_desc([size, color, name]);
  1246. };
  1247. this.describe = function (verbose = true) {
  1248. return defaultDescribe(verbose, this);
  1249. }
  1250. }
  1251. function HelicopterHangar(count = 1) {
  1252. this.name = "Helicopter Hangar";
  1253. copy_defaults(this, new DefaultEntity());
  1254. this.count = count;
  1255. this.contents = initContents(this.name, this.count);
  1256. this.describeOne = function (verbose = true) {
  1257. var size = random_desc(["weathered", "aging", "new"], (verbose ? 0.5 : 0));
  1258. var color = random_desc(["blue", "white", "gray", "tan", "green"], (verbose ? 0.5 : 0));
  1259. var name = random_desc(["hangar", "hangar", "hangar", "helicopter hangar"], 1);
  1260. return merge_desc([size, color, name]);
  1261. };
  1262. this.describe = function (verbose = true) {
  1263. return defaultDescribe(verbose, this);
  1264. }
  1265. }
  1266. function LargeHangar(count = 1) {
  1267. this.name = "Large Hangar";
  1268. copy_defaults(this, new DefaultEntity());
  1269. this.count = count;
  1270. this.contents = initContents(this.name, this.count);
  1271. this.describeOne = function (verbose = true) {
  1272. var size = random_desc(["weathered", "aging", "new"], (verbose ? 0.5 : 0));
  1273. var color = random_desc(["blue", "white", "gray", "tan", "green"], (verbose ? 0.5 : 0));
  1274. var name = random_desc(["hangar", "hangar", "hangar", "large hangar", "spacious hangar"], 1);
  1275. return merge_desc([size, color, name]);
  1276. };
  1277. this.describe = function (verbose = true) {
  1278. return defaultDescribe(verbose, this);
  1279. }
  1280. }
  1281. function SmallSkyscraper(count = 1) {
  1282. this.name = "Small Skyscraper";
  1283. copy_defaults(this, new DefaultEntity());
  1284. this.count = count;
  1285. this.contents = initContents(this.name, this.count);
  1286. this.describeOne = function (verbose = true) {
  1287. var color = random_desc(["blue", "white", "gray", "tan", "green"], (verbose ? 0.5 : 0));
  1288. var name = random_desc(["skyscraper", "office tower", "office building", "high rise"], 1);
  1289. return merge_desc([color, name]);
  1290. };
  1291. this.describe = function (verbose = true) {
  1292. return defaultDescribe(verbose, this);
  1293. }
  1294. }
  1295. function LargeSkyscraper(count = 1) {
  1296. this.name = "Large Skyscraper";
  1297. copy_defaults(this, new DefaultEntity());
  1298. this.count = count;
  1299. this.contents = initContents(this.name, this.count);
  1300. this.describeOne = function (verbose = true) {
  1301. var color = random_desc(["blue", "white", "gray", "tan", "green", "glass"], (verbose ? 0.5 : 0));
  1302. var name = random_desc(["skyscraper", "office tower", "office building"], 1);
  1303. return merge_desc(["towering", color, name]);
  1304. };
  1305. this.describe = function (verbose = true) {
  1306. return defaultDescribe(verbose, this);
  1307. }
  1308. }
  1309. function ParkingGarage(count = 1) {
  1310. this.name = "Parking Garage";
  1311. copy_defaults(this, new DefaultEntity());
  1312. this.count = count;
  1313. this.contents = initContents(this.name, this.count);
  1314. this.describe = function (verbose = true) {
  1315. return defaultDescribe(verbose, this);
  1316. }
  1317. }
  1318. function Ranch(count = 1) {
  1319. this.name = "Ranch";
  1320. copy_defaults(this, new DefaultEntity());
  1321. this.count = count;
  1322. this.contents = initContents(this.name, this.count);
  1323. this.describeOne = function (verbose = true) {
  1324. var size = random_desc(["little", "large", "prosperous", "run-down"], (verbose ? 0.5 : 0));
  1325. var name = random_desc(["ranch", "farm", "ranch", "dairy farm", "cattle farm", "ranch", "farm"], 1);
  1326. return merge_desc([size, name]);
  1327. };
  1328. this.describe = function (verbose = true) {
  1329. return defaultDescribe(verbose, this);
  1330. }
  1331. }
  1332. function Airstrip(count = 1) {
  1333. this.name = "Airstrip";
  1334. copy_defaults(this, new DefaultEntity());
  1335. this.count = count;
  1336. this.contents = initContents(this.name, this.count);
  1337. this.describe = function (verbose = true) {
  1338. return defaultDescribe(verbose, this, "community");
  1339. }
  1340. }
  1341. function Airport(count = 1) {
  1342. this.name = "Airport";
  1343. copy_defaults(this, new DefaultEntity());
  1344. this.count = count;
  1345. this.contents = initContents(this.name, this.count);
  1346. this.describe = function (verbose = true) {
  1347. return defaultDescribe(verbose, this, "community");
  1348. }
  1349. }
  1350. function Town(count = 1) {
  1351. this.name = "Town";
  1352. copy_defaults(this, new DefaultEntity());
  1353. this.count = count;
  1354. this.contents = initContents(this.name, this.count);
  1355. this.describe = function (verbose = true) {
  1356. return defaultDescribe(verbose, this, "community");
  1357. }
  1358. }
  1359. function City(count = 1) {
  1360. this.name = "City";
  1361. copy_defaults(this, new DefaultEntity());
  1362. this.count = count;
  1363. this.contents = initContents(this.name, this.count);
  1364. this.describe = function (verbose = true) {
  1365. return defaultDescribe(verbose, this, "community");
  1366. }
  1367. }
  1368. function Continent(count = 1) {
  1369. this.name = "Continent";
  1370. copy_defaults(this, new DefaultEntity());
  1371. this.count = count;
  1372. this.contents = initContents(this.name, this.count);
  1373. this.describe = function (verbose = true) {
  1374. return defaultDescribe(verbose, this, "community");
  1375. }
  1376. }
  1377. function Planet(count = 1) {
  1378. this.name = "Planet";
  1379. copy_defaults(this, new DefaultEntity());
  1380. this.count = count;
  1381. this.contents = initContents(this.name, this.count);
  1382. this.describe = function (verbose = true) {
  1383. return defaultDescribe(verbose, this, "community");
  1384. }
  1385. }
  1386. function Star(count = 1) {
  1387. this.name = "Star";
  1388. copy_defaults(this, new DefaultEntity());
  1389. this.count = count;
  1390. this.contents = initContents(this.name, this.count);
  1391. this.describe = function (verbose = true) {
  1392. return (this.count == 1 ? "a star" : this.count + " stars");
  1393. };
  1394. }
  1395. function SolarSystem(count = 1) {
  1396. this.name = "Solar System";
  1397. copy_defaults(this, new DefaultEntity());
  1398. this.count = count;
  1399. this.contents = initContents(this.name, this.count);
  1400. this.describe = function (verbose = true) {
  1401. return defaultDescribe(verbose, this, "celestial");
  1402. }
  1403. }
  1404. function Galaxy(count = 1) {
  1405. this.name = "Galaxy";
  1406. copy_defaults(this, new DefaultEntity());
  1407. this.count = count;
  1408. this.contents = initContents(this.name, this.count);
  1409. this.describe = function (verbose = true) {
  1410. return defaultDescribe(verbose, this, "celestial");
  1411. }
  1412. }
  1413. function Cluster(count = 1) {
  1414. this.name = "Cluster";
  1415. copy_defaults(this, new DefaultEntity());
  1416. this.count = count;
  1417. this.contents = initContents(this.name, this.count);
  1418. this.describe = function (verbose = true) {
  1419. return defaultDescribe(verbose, this, "celestial");
  1420. }
  1421. }
  1422. function Universe(count = 1) {
  1423. this.name = "Universe";
  1424. copy_defaults(this, new DefaultEntity());
  1425. this.count = count;
  1426. this.contents = initContents(this.name, this.count);
  1427. this.describe = function (verbose = true) {
  1428. return defaultDescribe(verbose, this, "celestial");
  1429. }
  1430. }
  1431. function Multiverse(count = 1) {
  1432. this.name = "Multiverse";
  1433. copy_defaults(this, new DefaultEntity());
  1434. this.count = count;
  1435. this.contents = initContents(this.name, this.count);
  1436. this.describe = function (verbose = true) {
  1437. return defaultDescribe(verbose, this, "celestial");
  1438. }
  1439. }
  1440. function Timeline(count = 1) {
  1441. this.name = "Timeline";
  1442. copy_defaults(this, new DefaultEntity());
  1443. this.count = count;
  1444. this.contents = initContents(this.name, this.count);
  1445. this.describe = function (verbose = true) {
  1446. return defaultDescribe(verbose, this, "celestial");
  1447. }
  1448. }
  1449. function Pantheon(count = 1) {
  1450. this.name = "Pantheon";
  1451. copy_defaults(this, new DefaultEntity());
  1452. this.count = count;
  1453. this.contents = initContents(this.name, this.count);
  1454. this.describe = function (verbose = true) {
  1455. return defaultDescribe(verbose, this, "celestial");
  1456. }
  1457. }
  1458. function Deity(count = 1) {
  1459. this.name = "Deity";
  1460. copy_defaults(this, new DefaultEntity());
  1461. this.count = count;
  1462. this.contents = initContents(this.name, this.count);
  1463. this.describe = function (verbose = true) {
  1464. return defaultDescribe(verbose, this, "celestial");
  1465. }
  1466. }
  1467. function Reality(count = 1) {
  1468. this.name = "Reality";
  1469. copy_defaults(this, new DefaultEntity());
  1470. this.count = count;
  1471. this.contents = initContents(this.name, this.count);
  1472. this.describe = function (verbose = true) {
  1473. return defaultDescribe(verbose, this, "celestial");
  1474. }
  1475. }
  1476. function Soldier(count = 1) {
  1477. this.name = "Soldier";
  1478. copy_defaults(this, new DefaultEntity());
  1479. this.count = count;
  1480. this.contents = initContents(this.name, this.count);
  1481. this.describe = function (verbose = true) {
  1482. return defaultDescribe(verbose, this, "military");
  1483. }
  1484. }
  1485. function Tank(count = 1) {
  1486. this.name = "Tank";
  1487. copy_defaults(this, new DefaultEntity());
  1488. this.count = count;
  1489. this.contents = initContents(this.name, this.count);
  1490. this.describe = function (verbose = true) {
  1491. return defaultDescribe(verbose, this, "generic vehicle");
  1492. }
  1493. }
  1494. function Artillery(count = 1) {
  1495. this.name = "Artillery";
  1496. copy_defaults(this, new DefaultEntity());
  1497. this.count = count;
  1498. this.contents = initContents(this.name, this.count);
  1499. this.describe = function (verbose = true) {
  1500. return defaultDescribe(verbose, this, "generic vehicle");
  1501. }
  1502. }
  1503. function MilitaryHelicopter(count = 1) {
  1504. this.name = "Military Helicopter";
  1505. copy_defaults(this, new DefaultEntity());
  1506. this.count = count;
  1507. this.contents = initContents(this.name, this.count);
  1508. this.describe = function (verbose = true) {
  1509. return defaultDescribe(verbose, this, "generic vehicle");
  1510. }
  1511. }
  1512. function Micro(count = 1) {
  1513. this.name = "Micro";
  1514. copy_defaults(this, new DefaultEntity());
  1515. this.count = count;
  1516. this.contents = initContents(this.name, this.count);
  1517. this.describe = function (verbose = true) {
  1518. return defaultDescribe(verbose, this);
  1519. }
  1520. }
  1521. function Macro(count = 1) {
  1522. this.name = "Macro";
  1523. copy_defaults(this, new DefaultEntity());
  1524. this.count = count;
  1525. this.contents = initContents(this.name, this.count);
  1526. this.describe = function (verbose = true) {
  1527. return defaultDescribe(verbose, this);
  1528. }
  1529. }
  1530. function Squad(count = 1) {
  1531. this.name = "Squad";
  1532. copy_defaults(this, new DefaultEntity());
  1533. this.count = count;
  1534. this.contents = initContents(this.name, this.count);
  1535. this.describe = function (verbose = true) {
  1536. return defaultDescribe(verbose, this, "military");
  1537. }
  1538. }
  1539. function Platoon(count = 1) {
  1540. this.name = "Platoon";
  1541. copy_defaults(this, new DefaultEntity());
  1542. this.count = count;
  1543. this.contents = initContents(this.name, this.count);
  1544. this.describe = function (verbose = true) {
  1545. return defaultDescribe(verbose, this, "military");
  1546. }
  1547. }
  1548. function Company(count = 1) {
  1549. this.name = "Company";
  1550. copy_defaults(this, new DefaultEntity());
  1551. this.count = count;
  1552. this.contents = initContents(this.name, this.count);
  1553. this.describe = function (verbose = true) {
  1554. return defaultDescribe(verbose, this, "military");
  1555. }
  1556. }
  1557. function Battalion(count = 1) {
  1558. this.name = "Battalion";
  1559. copy_defaults(this, new DefaultEntity());
  1560. this.count = count;
  1561. this.contents = initContents(this.name, this.count);
  1562. this.describe = function (verbose = true) {
  1563. return defaultDescribe(verbose, this, "military");
  1564. }
  1565. }
  1566. function Brigade(count = 1) {
  1567. this.name = "Brigade";
  1568. copy_defaults(this, new DefaultEntity());
  1569. this.count = count;
  1570. this.contents = initContents(this.name, this.count);
  1571. this.describe = function (verbose = true) {
  1572. return defaultDescribe(verbose, this, "military");
  1573. }
  1574. }
  1575. function Division(count = 1) {
  1576. this.name = "Division";
  1577. copy_defaults(this, new DefaultEntity());
  1578. this.count = count;
  1579. this.contents = initContents(this.name, this.count);
  1580. this.describe = function (verbose = true) {
  1581. return defaultDescribe(verbose, this, "military");
  1582. }
  1583. }
  1584. function TankDivision(count = 1) {
  1585. this.name = "Tank Division";
  1586. copy_defaults(this, new DefaultEntity());
  1587. this.count = count;
  1588. this.contents = initContents(this.name, this.count);
  1589. this.describe = function (verbose = true) {
  1590. return defaultDescribe(verbose, this, "military");
  1591. }
  1592. }
  1593. function Army(count = 1) {
  1594. this.name = "Army";
  1595. copy_defaults(this, new DefaultEntity());
  1596. this.count = count;
  1597. this.contents = initContents(this.name, this.count);
  1598. this.describe = function (verbose = true) {
  1599. return defaultDescribe(verbose, this, "military");
  1600. }
  1601. }
  1602. //todo
  1603. //farms
  1604. //factories
  1605. //racetracks
  1606. //more building types
  1607. //cranes and other construction equipment
  1608. //nebula
  1609. //biome magic also set it so that you can't roll your existing biome
  1610. //chemical factory
  1611. //grand army
  1612. //armada