summary refs log tree commit diff stats
path: root/lingo.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lingo.cpp')
-rw-r--r--lingo.cpp82
1 files changed, 79 insertions, 3 deletions
diff --git a/lingo.cpp b/lingo.cpp index 439bab5..5f8a025 100644 --- a/lingo.cpp +++ b/lingo.cpp
@@ -13,6 +13,7 @@
13#include <optional> 13#include <optional>
14#include <map> 14#include <map>
15#include <array> 15#include <array>
16#include "imagenet.h"
16 17
17#define ENABLE_BOT 18#define ENABLE_BOT
18 19
@@ -31,6 +32,7 @@ enum Colour {
31 kPurple, 32 kPurple,
32 kBrown, 33 kBrown,
33 kYellow, 34 kYellow,
35 kGreen,
34 kColourCount 36 kColourCount
35}; 37};
36 38
@@ -41,7 +43,8 @@ const std::string COLOUR_EMOJIS[kColourCount] = {
41 "🟦", 43 "🟦",
42 "🟪", 44 "🟪",
43 "🟫", 45 "🟫",
44 "🟨" 46 "🟨",
47 "🟩"
45}; 48};
46 49
47const std::string NONE_EMOTE = "<:xx:1047267830535557180>"; 50const std::string NONE_EMOTE = "<:xx:1047267830535557180>";
@@ -53,7 +56,8 @@ const std::string COLOUR_EMOTES[kColourCount] = {
53 "<:bl:1047262138202325042>", 56 "<:bl:1047262138202325042>",
54 "<:pr:1047262146926489691>", 57 "<:pr:1047262146926489691>",
55 "<:bn:1047262139187998790>", 58 "<:bn:1047262139187998790>",
56 "<:yw:1047262152781737986>" 59 "<:yw:1047262152781737986>",
60 "<:gn:1047262141914304633>"
57}; 61};
58 62
59enum FilterDirection { 63enum FilterDirection {
@@ -195,6 +199,50 @@ verbly::filter makeHintFilter(verbly::filter subfilter, Height height, Colour co
195 } 199 }
196 break; 200 break;
197 } 201 }
202 case kGreen: {
203 if (filter_direction == kTowardSolution)
204 {
205 verbly::filter whitelist =
206 (verbly::notion::wnid == 109287968) // Geological formations
207 || (verbly::notion::wnid == 109208496) // Asterisms (collections of stars)
208 || (verbly::notion::wnid == 109239740) // Celestial bodies
209 || (verbly::notion::wnid == 109277686) // Exterrestrial objects (comets and meteroids)
210 || (verbly::notion::wnid == 109403211) // Radiators (supposedly natural radiators but actually these are just pictures of radiators)
211 || (verbly::notion::wnid == 109416076) // Rocks
212 || (verbly::notion::wnid == 105442131) // Chromosomes
213 || (verbly::notion::wnid == 100324978) // Tightrope walking
214 || (verbly::notion::wnid == 100326094) // Rock climbing
215 || (verbly::notion::wnid == 100433458) // Contact sports
216 || (verbly::notion::wnid == 100433802) // Gymnastics
217 || (verbly::notion::wnid == 100439826) // Track and field
218 || (verbly::notion::wnid == 100440747) // Skiing
219 || (verbly::notion::wnid == 100441824) // Water sport
220 || (verbly::notion::wnid == 100445351) // Rowing
221 || (verbly::notion::wnid == 100446980) // Archery
222 // TODO: add more sports
223 || (verbly::notion::wnid == 100021939) // Artifacts
224 || (verbly::notion::wnid == 101471682) // Vertebrates
225 ;
226
227 verbly::filter blacklist =
228 (verbly::notion::wnid == 106883725) // swastika
229 || (verbly::notion::wnid == 104416901) // tetraskele
230 || (verbly::notion::wnid == 102512053) // fish
231 || (verbly::notion::wnid == 103575691) // instrument of execution
232 || (verbly::notion::wnid == 103829563) // noose
233 || (verbly::notion::wnid == 103663910) // life support
234 ;
235
236 return subfilter
237 && (verbly::notion::fullHypernyms %= whitelist)
238 && !(verbly::notion::fullHypernyms %= blacklist)
239 && (verbly::notion::partOfSpeech == verbly::part_of_speech::noun)
240 && (verbly::notion::numOfImages >= 1);
241 } else {
242 return (verbly::form::text == "picture");
243 }
244 break;
245 }
198 default: break; // Not supported yet. 246 default: break; // Not supported yet.
199 } 247 }
200 return {}; 248 return {};
@@ -255,6 +303,7 @@ public:
255 dpp::snowflake channel(config["discord_channel"].as<uint64_t>()); 303 dpp::snowflake channel(config["discord_channel"].as<uint64_t>());
256 304
257 database_ = std::make_unique<verbly::database>(config["verbly_datafile"].as<std::string>()); 305 database_ = std::make_unique<verbly::database>(config["verbly_datafile"].as<std::string>());
306 imagenet_ = std::make_unique<imagenet>(config["imagenet"].as<std::string>());
258 307
259 for (;;) 308 for (;;)
260 { 309 {
@@ -278,10 +327,12 @@ private:
278 {kMiddle, kRed}, 327 {kMiddle, kRed},
279 {kMiddle, kBlue}, 328 {kMiddle, kBlue},
280 {kMiddle, kPurple}, 329 {kMiddle, kPurple},
330 {kMiddle, kGreen},
281 {kBottom, kWhite}, 331 {kBottom, kWhite},
282 {kBottom, kBlack}, 332 {kBottom, kBlack},
283 {kBottom, kRed}, 333 {kBottom, kRed},
284 {kBottom, kBlue}, 334 {kBottom, kBlue},
335 {kBottom, kGreen},
285 }; 336 };
286 337
287 std::set<std::tuple<Height, Colour>> expensive_hints = { 338 std::set<std::tuple<Height, Colour>> expensive_hints = {
@@ -313,6 +364,7 @@ private:
313 int non_purple_uses = 0; 364 int non_purple_uses = 0;
314 int expensive_uses = 0; 365 int expensive_uses = 0;
315 int moderate_uses = 0; 366 int moderate_uses = 0;
367 int green_uses = 0;
316 std::array<std::optional<Colour>, kHeightCount> parts; 368 std::array<std::optional<Colour>, kHeightCount> parts;
317 for (int height = 0; height < static_cast<int>(kHeightCount); height++) { 369 for (int height = 0; height < static_cast<int>(kHeightCount); height++) {
318 if (std::bernoulli_distribution(0.5)(rng_)) { 370 if (std::bernoulli_distribution(0.5)(rng_)) {
@@ -334,6 +386,10 @@ private:
334 { 386 {
335 moderate_uses++; 387 moderate_uses++;
336 } 388 }
389 if (colour == kGreen)
390 {
391 green_uses++;
392 }
337 393
338 std::cout << COLOUR_EMOJIS[colour]; 394 std::cout << COLOUR_EMOJIS[colour];
339 } else { 395 } else {
@@ -359,6 +415,11 @@ private:
359 std::cout << "Moderate hints can't be combined with an expensive hint." << std::endl; 415 std::cout << "Moderate hints can't be combined with an expensive hint." << std::endl;
360 continue; 416 continue;
361 } 417 }
418 if (green_uses != 1)
419 {
420 std::cout << "Too many green hints." << std::endl;
421 continue;
422 }
362 423
363 verbly::filter forwardFilter = cleanFilter && (verbly::form::proper == false); 424 verbly::filter forwardFilter = cleanFilter && (verbly::form::proper == false);
364 for (int i=0; i<static_cast<int>(kHeightCount); i++) { 425 for (int i=0; i<static_cast<int>(kHeightCount); i++) {
@@ -401,10 +462,24 @@ private:
401 std::cout << message_text << std::endl << std::endl << solution.getText() << std::endl; 462 std::cout << message_text << std::endl << std::endl << solution.getText() << std::endl;
402 463
403 std::vector<verbly::form> admissibleResults = database_->forms(admissible, {}, 10).all(); 464 std::vector<verbly::form> admissibleResults = database_->forms(admissible, {}, 10).all();
404 if (admissibleResults.size() <= (hints == 1 ? 2 : 5)) 465 if (green_uses > 0 || (admissibleResults.size() <= (hints == 1 ? 2 : 5)))
405 { 466 {
406#ifdef ENABLE_BOT 467#ifdef ENABLE_BOT
407 dpp::message message(channel, message_text); 468 dpp::message message(channel, message_text);
469
470 if (green_uses > 0)
471 {
472 verbly::notion notion = database_->notions(
473 (verbly::notion::numOfImages > 1) && solution).first();
474 auto [image, extension] = imagenet_->getImageForNotion(notion.getId(), rng_);
475 if (image.empty())
476 {
477 throw std::runtime_error("Could not find image for green hint.");
478 }
479
480 message.add_file(std::string("SPOILER_image.") + extension, image);
481 }
482
408 bot_->message_create(message, [this, &solution](const dpp::confirmation_callback_t& userdata) { 483 bot_->message_create(message, [this, &solution](const dpp::confirmation_callback_t& userdata) {
409 const auto& posted_msg = std::get<dpp::message>(userdata.value); 484 const auto& posted_msg = std::get<dpp::message>(userdata.value);
410 std::lock_guard answer_lock(answers_mutex_); 485 std::lock_guard answer_lock(answers_mutex_);
@@ -432,6 +507,7 @@ private:
432 std::mt19937& rng_; 507 std::mt19937& rng_;
433 std::unique_ptr<dpp::cluster> bot_; 508 std::unique_ptr<dpp::cluster> bot_;
434 std::unique_ptr<verbly::database> database_; 509 std::unique_ptr<verbly::database> database_;
510 std::unique_ptr<imagenet> imagenet_;
435 std::map<uint64_t, std::string> answer_by_message_; 511 std::map<uint64_t, std::string> answer_by_message_;
436 std::mutex answers_mutex_; 512 std::mutex answers_mutex_;
437}; 513};