about summary refs log tree commit diff stats
path: root/data/maps/the_double_sided/rooms/Flipped Blue Area.txtpb
diff options
context:
space:
mode:
authorStar Rauchenberger <fefferburbia@gmail.com>2025-08-30 18:35:55 -0400
committerStar Rauchenberger <fefferburbia@gmail.com>2025-08-30 18:35:55 -0400
commit8ad846ce1ea9e12026512ea81f4baf1309d2b6d8 (patch)
tree96c047abfeb30e4164c8b451ad9f84c9629249dd /data/maps/the_double_sided/rooms/Flipped Blue Area.txtpb
parentd64ce785a7f1ca4e26b85499a9cd310ed80fb80c (diff)
downloadlingo2-archipelago-8ad846ce1ea9e12026512ea81f4baf1309d2b6d8.tar.gz
lingo2-archipelago-8ad846ce1ea9e12026512ea81f4baf1309d2b6d8.tar.bz2
lingo2-archipelago-8ad846ce1ea9e12026512ea81f4baf1309d2b6d8.zip
[Client] Potentially fixed crash when loading corrupted localdata
Diffstat (limited to 'data/maps/the_double_sided/rooms/Flipped Blue Area.txtpb')
0 files changed, 0 insertions, 0 deletions
#0066bb; font-weight: bold } /* Name.Function */ .highlight .nl { color: #336699; font-style: italic } /* Name.Label */ .highlight .nn { color: #bb0066; font-weight: bold } /* Name.Namespace */ .highlight .py { color: #336699; font-weight: bold } /* Name.Property */ .highlight .nt { color: #bb0066; font-weight: bold } /* Name.Tag */ .highlight .nv { color: #336699 } /* Name.Variable */ .highlight .ow { color: #008800 } /* Operator.Word */ .highlight .w { color: #bbbbbb } /* Text.Whitespace */ .highlight .mb { color: #0000DD; font-weight: bold } /* Literal.Number.Bin */ .highlight .mf { color: #0000DD; font-weight: bold } /* Literal.Number.Float */ .highlight .mh { color: #0000DD; font-weight: bold } /* Literal.Number.Hex */ .highlight .mi { color: #0000DD; font-weight: bold } /* Literal.Number.Integer */ .highlight .mo { color: #0000DD; font-weight: bold } /* Literal.Number.Oct */ .highlight .sa { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Affix */ .highlight .sb { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Backtick */ .highlight .sc { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Char */ .highlight .dl { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Delimiter */ .highlight .sd { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Doc */ .highlight .s2 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Double */ .highlight .se { color: #0044dd; background-color: #fff0f0 } /* Literal.String.Escape */ .highlight .sh { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Heredoc */ .highlight .si { color: #3333bb; background-color: #fff0f0 } /* Literal.String.Interpol */ .highlight .sx { color: #22bb22; background-color: #f0fff0 } /* Literal.String.Other */ .highlight .sr { color: #008800; background-color: #fff0ff } /* Literal.String.Regex */ .highlight .s1 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Single */ .highlight .ss { color: #aa6600; background-color: #fff0f0 } /* Literal.String.Symbol */ .highlight .bp { color: #003388 } /* Name.Builtin.Pseudo */ .highlight .fm { color: #0066bb; font-weight: bold } /* Name.Function.Magic */ .highlight .vc { color: #336699 } /* Name.Variable.Class */ .highlight .vg { color: #dd7700 } /* Name.Variable.Global */ .highlight .vi { color: #3333bb } /* Name.Variable.Instance */ .highlight .vm { color: #336699 } /* Name.Variable.Magic */ .highlight .il { color: #0000DD; font-weight: bold } /* Literal.Number.Integer.Long */
#include "imagenet.h"
#include <fstream>
#include <stdexcept>
#include <sstream>
#include <vector>
#include <curl_easy.h>
#include <curl_header.h>

imagenet::imagenet(std::string path) : path_(path) {}

std::tuple<std::string, std::string> imagenet::getImageForNotion(int notion_id, std::mt19937& rng) const
{
  std::filesystem::path filename = path_ / std::to_string(notion_id);
  if (!std::filesystem::exists(filename))
  {
    throw std::invalid_argument(std::string("File does not exist: ") + std::string(filename));
  }

  std::ifstream file(filename);
  std::string line;
  std::vector<std::string> urls;
  while (std::getline(file, line))
  {
    if (!line.empty())
    {
      urls.push_back(line);
    }
  }

  std::string output;
  std::string extension;
  while (!urls.empty())
  {
    int index = std::uniform_int_distribution<int>(0, urls.size()-1)(rng);
    std::string url = urls.at(index);
    urls.erase(std::begin(urls) + index);

    // willyfogg.com is a thumbnail generator known to return 200 even if the target image no longer exists
    if (url.find("willyfogg.com/thumb.php") != std::string::npos)
    {
      continue;
    }

    // Accept string from Google Chrome
    std::string accept = "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8";
    curl::curl_header headers;
    headers.add(accept);

    std::ostringstream imgbuf;
    curl::curl_ios<std::ostringstream> imgios(imgbuf);
    curl::curl_easy imghandle(imgios);

    imghandle.add<CURLOPT_HTTPHEADER>(headers.get());
    imghandle.add<CURLOPT_URL>(url.c_str());
    imghandle.add<CURLOPT_CONNECTTIMEOUT>(30);
    imghandle.add<CURLOPT_TIMEOUT>(300);

    try
    {
      imghandle.perform();
    } catch (const curl::curl_easy_exception& error) {
      error.print_traceback();

      continue;
    }

    if (imghandle.get_info<CURLINFO_RESPONSE_CODE>().get() != 200)
    {
      continue;
    }

    std::string content_type = imghandle.get_info<CURLINFO_CONTENT_TYPE>().get();
    if (content_type.substr(0, 6) != "image/")
    {
      continue;
    }

    output = imgbuf.str();
    extension = url.substr(url.rfind(".") + 1);
    break;
  }

  if (output.empty())
  {
    throw std::invalid_argument(std::string("No valid urls found for ") + std::string(filename));
  }

  return {output, extension};
}