ContentDescription.ts 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172
  1. class ContentDescription {
  2. public name : string;
  3. public group : ContentUnit | ContentGroup;
  4. public description : Say | ((description : ContentDescription, group : ContentUnit | ContentGroup) => Say);
  5. private saidCount = 0;
  6. public constructor (name : string, group : ContentUnit | ContentGroup) {
  7. this.name = name;
  8. this.group = group;
  9. }
  10. public getScore () {
  11. return (this.group).getScore();
  12. }
  13. public getDescription (group : ContentUnit | ContentGroup) : Say {
  14. this.saidCount++;
  15. if (typeof this.description == "function") {
  16. return this.description(this, group);
  17. }
  18. return this.description;
  19. }
  20. public setDescription (description : Say | string | ((description : ContentDescription, group : ContentUnit | ContentGroup) => Say) ) {
  21. if (!(description instanceof Say)) {
  22. this.description = new Say(description);
  23. } else {
  24. this.description = description;
  25. }
  26. return this;
  27. }
  28. public static pickDescriptions (cda : Array<ContentDescription>, target : ContentGroup | ContentUnit) : Array<Say> {
  29. let a = cda.slice();
  30. let groups = [];
  31. for (let i = 0; i < a.length; i++) {
  32. let randomIndex = Math.floor(Math.random() * (a.length - i)) + i;
  33. let temp = a[i];
  34. a[i] = a[randomIndex];
  35. a[randomIndex] = temp;
  36. }
  37. // After shuffling the list, descriptions with the highest scores go at the top, and between those the ones with the lowest saidCounts go first
  38. // If multiple descriptions have the same score/saidCount, they are picked randomly due to the previous shuffling.
  39. a.sort((a : ContentDescription, b : ContentDescription) => {
  40. // Division by saidCount for now, to increase rotativity of descriptions
  41. // Reduce precision on final number to decrease the likelihood of printing the same descriptions always in the same order
  42. let precision = 5;
  43. let scoreA = Math.floor(precision * a.getScore() / (a.saidCount + 1)) / precision;
  44. let scoreB = Math.floor(precision * b.getScore() / (b.saidCount + 1)) / precision;
  45. if (scoreA != scoreB) return scoreB - scoreA;
  46. return 0;
  47. });
  48. a.forEach(description => {
  49. groups.push(description.group);
  50. });
  51. let matches = (<any> target).matchAgainst(<any> groups);
  52. if (matches != undefined) {
  53. let result = [];
  54. matches.forEach(i => {
  55. result.push(a[i].getDescription(target));
  56. result.push(new Say(" "));
  57. });
  58. return result;
  59. } else {
  60. console.warn("No description available for", target);
  61. return [new Say("Warning: No description available for the current situation. Please report so it can be corrected.")];
  62. }
  63. }
  64. }