diff --git a/src/args.cpp b/src/args.cpp index ba6f2b3..58b20bc 100644 --- a/src/args.cpp +++ b/src/args.cpp @@ -14,6 +14,7 @@ const struct argp_option options[] = { //name, key, arg, flags, doc, group {"haar-cascade", 0x00, 0, 0, "Use Haar Cascades for faster (but less accurate) face detection.", 0}, {"show-camera", 0x01, 0, 0, "Show the camera feed in another window", 0}, + {"no-eyes", 0x02, 0, 0, "Disable eye tracking for better performance.", 0}, {"model", 'm', "model", 0, "Name of the model file to use. (not including '.fma')", 0}, // this option actually selects the minimum camera id to use, // i.e. instead of trying video0, video1, ... it will try @@ -32,6 +33,7 @@ struct argp argp = { #endif struct optData optData = { + false, false, false, "test", @@ -50,6 +52,10 @@ error_t parseOptions(int key, char* arg, struct argp_state* state) { optData.showCamera = true; break; + case 0x02: //--no-eyes + optData.noEyes = true; + break; + case 'm': optData.model = std::string(arg); break; diff --git a/src/args.hpp b/src/args.hpp index a007e4d..111a8db 100644 --- a/src/args.hpp +++ b/src/args.hpp @@ -12,6 +12,7 @@ error_t parseOptions(int key, char* arg, struct argp_state* state); struct optData { bool useHaar; // use haar cascades (0x00) bool showCamera; // show camera feed (0x01) + bool noEyes; // disable eye tracking (0x02) std::string model; // model to open (0x6d 'm') int minCameraID; // camera id to start search on (0x63 'c') }; diff --git a/src/configfile.cpp b/src/configfile.cpp index eaff972..bfec651 100644 --- a/src/configfile.cpp +++ b/src/configfile.cpp @@ -20,6 +20,10 @@ bool configFileOpen(struct optData* data) { if (showCameraResult.first) { data->showCamera = showCameraResult.second; } + auto noEyesResult = configFile.table->getBool("no_eyes"); + if (noEyesResult.first) { + data->noEyes = noEyesResult.second; + } auto modelNameResult = configFile.table->getString("model"); if (modelNameResult.first) { data->model = modelNameResult.second; diff --git a/src/cv.cpp b/src/cv.cpp index 6a908c1..09f345b 100644 --- a/src/cv.cpp +++ b/src/cv.cpp @@ -172,7 +172,10 @@ void cvFrame() { cv::Mat eyeROI; eyeROI = gray(eyeRect); - glm::vec2 eyeVector = eyeDirection(eyeROI); + glm::vec2 eyeVector(0,0); + if (!optData.noEyes) { + eyeVector = eyeDirection(eyeROI); // run pupil tracking algorithm and get look direction + } //send control information to graphics float faceSize = landmarks[biggestFace][14].x - landmarks[biggestFace][2].x; diff --git a/src/fc2dconfig.cpp b/src/fc2dconfig.cpp index 93b59a5..19930c6 100644 --- a/src/fc2dconfig.cpp +++ b/src/fc2dconfig.cpp @@ -24,6 +24,7 @@ class ConfigurationFrame : public wxFrame { std::vector modelVec; wxCheckBox* useHaarCheckBox; wxCheckBox* showCameraCheckBox; + wxCheckBox* noEyesCheckBox; wxChoice* modelNameChoice; wxSpinCtrl* cameraSpinCtrl; void loadExistingConfig(); // loads existing config file and populates controls @@ -56,6 +57,7 @@ ConfigurationFrame::ConfigurationFrame() : wxFrame(NULL, wxID_ANY, "Configure " // define all controls and labels useHaarCheckBox = new wxCheckBox(panel, wxID_ANY, "Disable DNN face detection"); showCameraCheckBox = new wxCheckBox(panel, wxID_ANY, "Show camera feed"); + noEyesCheckBox = new wxCheckBox(panel, wxID_ANY, "Disable eye tracking"); wxStaticText* modelNameText = new wxStaticText(panel, wxID_ANY, "Model name:"); modelNameChoice = new wxChoice(panel, wxID_ANY, wxDefaultPosition, wxDefaultSize, modelVec.size(), modelArray); wxStaticText* cameraText = new wxStaticText(panel, wxID_ANY, "Camera ID:"); @@ -69,13 +71,17 @@ ConfigurationFrame::ConfigurationFrame() : wxFrame(NULL, wxID_ANY, "Configure " cameraSizer->Add(cameraText, 0, wxALIGN_CENTER | wxALL, 5); cameraSizer->Add(cameraSpinCtrl, 0, wxLEFT, 20); + + // General section wxStaticBoxSizer* generalBoxSizer = new wxStaticBoxSizer(new wxStaticBox(panel, wxID_ANY, "General"), wxVERTICAL); generalBoxSizer->Add(modelSizer, 0, wxALL, 5); generalBoxSizer->Add(cameraSizer, 0, wxALL, 5); generalBoxSizer->Add(showCameraCheckBox, 0, wxALL, 5); + // Performance section wxStaticBoxSizer* performanceBoxSizer = new wxStaticBoxSizer(new wxStaticBox(panel, wxID_ANY, "Performance"), wxVERTICAL); performanceBoxSizer->Add(useHaarCheckBox, 0, wxALL, 5); + performanceBoxSizer->Add(noEyesCheckBox, 0, wxALL, 5); // define bottom buttons (Cancel and Apply) and their sizer wxButton* cancelButton = new wxButton(panel, wxID_CANCEL, "Cancel"); @@ -105,6 +111,7 @@ void ConfigurationFrame::loadExistingConfig() { useHaarCheckBox->SetValue(configData.useHaar); showCameraCheckBox->SetValue(configData.showCamera); + noEyesCheckBox->SetValue(configData.noEyes); for (int i = 0; i < modelVec.size(); i++) { if (modelVec[i] == configData.model) { modelNameChoice->SetSelection(i); @@ -120,6 +127,7 @@ void ConfigurationFrame::OnApply(wxCommandEvent& event) { configFile.open(prefixConfig + "config.toml"); configFile << "use_haar = " << (useHaarCheckBox->GetValue() ? "true" : "false") << std::endl; configFile << "show_camera = " << (showCameraCheckBox->GetValue() ? "true" : "false") << std::endl; + configFile << "no_eyes = " << (noEyesCheckBox->GetValue() ? "true" : "false") << std::endl; // janky edge case lmao // if user did not select any model, don't write the line in the config file! if (modelNameChoice->GetSelection() != wxNOT_FOUND) {