Added filtering by ingredient to search window.

This commit is contained in:
Andrew Lalis 2018-03-30 20:57:14 +02:00
parent e0dda64412
commit 4170df7fc8
4 changed files with 51 additions and 19 deletions

View File

@ -11,17 +11,17 @@ OpenRecipeDialog::OpenRecipeDialog(QWidget *parent) :
ui->ingredientsListView->setModel(&this->ingredientsModel);
ui->tagsListView->setModel(&this->tagsModel);
connect(ui->ingredientsListView->selectionModel(),
QObject::connect(ui->ingredientsListView->selectionModel(),
SIGNAL(selectionChanged(QItemSelection, QItemSelection)),
this,
SLOT(on_ingredientsListView_selectionChanged(QItemSelection)));
SLOT(onIngredientsListViewSelectionChanged(QItemSelection)));
}
OpenRecipeDialog::OpenRecipeDialog(RecipeDatabase *recipeDB, QWidget *parent) : OpenRecipeDialog(parent){
this->recipeDB = recipeDB;
this->populateIngredientsList();
this->populateTagsList();
this->populateRecipesTable();
this->populateRecipesTable(this->recipeDB->retrieveAllRecipes());
}
OpenRecipeDialog::~OpenRecipeDialog()
@ -33,9 +33,8 @@ Recipe OpenRecipeDialog::getSelectedRecipe(){
return this->selectedRecipe;
}
void OpenRecipeDialog::populateRecipesTable(){
void OpenRecipeDialog::populateRecipesTable(vector<Recipe> recipes){
this->recipeTableModel.clear();
vector<Recipe> recipes = this->recipeDB->retrieveAllRecipes();
this->recipeTableModel.setRecipes(recipes);
ui->recipeTableView->resizeColumnsToContents();
ui->recipeTableView->show();
@ -69,9 +68,10 @@ void OpenRecipeDialog::on_deleteRecipeButton_clicked(){
bool success = this->recipeDB->deleteRecipe(r.getName());
if (!success){
QMessageBox::critical(this, QString::fromStdString("Unable to Delete"), QString::fromStdString("Could not delete recipe "+r.getName()));
} else {
this->populateRecipesTable(this->recipeDB->retrieveAllRecipes());
}
}
this->populateRecipesTable();
}
}
@ -80,13 +80,12 @@ void OpenRecipeDialog::on_recipeTableView_doubleClicked(const QModelIndex &index
this->close();
}
void OpenRecipeDialog::on_ingredientsListView_selectionChanged(const QItemSelection &selection){
printf("Selection changed!\n");
void OpenRecipeDialog::onIngredientsListViewSelectionChanged(const QItemSelection &selection){
vector<Ingredient> ingredients;
for (QModelIndex index : selection.indexes()){
QModelIndexList indexes = ui->ingredientsListView->selectionModel()->selectedRows();
for (QModelIndex index : indexes){
Ingredient i = this->ingredientsModel.getIngredients().at(index.row());
ingredients.push_back(i);
printf("Selected: %s\n", i.getName().c_str());
}
this->populateRecipesTable(this->recipeDB->retrieveRecipesWithIngredients(ingredients));
}

View File

@ -30,7 +30,7 @@ class OpenRecipeDialog : public QDialog
void on_recipeTableView_doubleClicked(const QModelIndex &index);
void on_ingredientsListView_selectionChanged(const QItemSelection &selection);
void onIngredientsListViewSelectionChanged(const QItemSelection &selection);
private:
Ui::OpenRecipeDialog *ui;
@ -41,7 +41,7 @@ class OpenRecipeDialog : public QDialog
IngredientListModel ingredientsModel;
TagListModel tagsModel;
void populateRecipesTable();
void populateRecipesTable(vector<Recipe> recipes);
void populateIngredientsList();
void populateTagsList();
};

View File

@ -158,15 +158,36 @@ Recipe RecipeDatabase::retrieveRandomRecipe(){
}
return this->readFromResultTable(t);
}
//TODO: Change this to be more efficient! One query per recipe is not good!
vector<Recipe> RecipeDatabase::retrieveAllRecipes(){
ResultTable t = this->selectFrom("recipe", "name", "ORDER BY name");
vector<Recipe> recipes;
for (TableRow row : t.rows()){
recipes.push_back(this->retrieveRecipe(row.at(0)));
ResultTable t = this->executeSQL("SELECT * FROM recipe ORDER BY name;");
return this->readRecipesFromTable(t);
}
vector<Recipe> RecipeDatabase::retrieveRecipesWithIngredients(vector<Ingredient> ingredients){
vector<Recipe> recipes;
if (ingredients.empty()){
return recipes;
}
string filterList = surroundString(ingredients.at(0).getName(), "'");
for (unsigned int i = 1; i < ingredients.size(); i++){
filterList += ", " + surroundString(ingredients[i].getName(), "'");
}
filterList = '(' + filterList + ')';
ResultTable t = this->executeSQL("SELECT * "
"FROM recipe "
"WHERE recipeId IN ("
" SELECT recipeIngredient.recipeId "
" FROM recipeIngredient "
" INNER JOIN ("
" SELECT ingredientId "
" FROM ingredient "
" WHERE name IN "+filterList+""
" ) filteredIngredients "
" ON recipeIngredient.ingredientId = filteredIngredients.ingredientId"
") ORDER BY name;");
return this->readRecipesFromTable(t);
}
vector<string> RecipeDatabase::retrieveAllFoodGroups(){
ResultTable t = this->executeSQL("SELECT DISTINCT foodGroup FROM ingredient ORDER BY foodGroup;");
@ -360,3 +381,13 @@ Recipe RecipeDatabase::readFromResultTable(ResultTable t, int tRow){
r.setTags(this->retrieveTags(id));
return r;
}
//Retrieves recipes from a table with the following format:
// id, name, createdDate, prepTime, cookTime, servings
vector<Recipe> RecipeDatabase::readRecipesFromTable(ResultTable t){
vector<Recipe> recipes;
for (unsigned int row = 0; row < t.rowCount(); row++){
recipes.push_back(readFromResultTable(t, row));
}
return recipes;
}

View File

@ -34,6 +34,7 @@ class RecipeDatabase : public Database
Recipe retrieveRecipe(string name);
Recipe retrieveRandomRecipe();
vector<Recipe> retrieveAllRecipes();
vector<Recipe> retrieveRecipesWithIngredients(vector<Ingredient> ingredients);
vector<string> retrieveAllFoodGroups();
vector<RecipeIngredient> retrieveRecipeIngredients(int recipeId);
vector<Ingredient> retrieveAllIngredients();
@ -53,6 +54,7 @@ class RecipeDatabase : public Database
void ensureTablesExist();
//Read a recipe from a row of a result table.
Recipe readFromResultTable(ResultTable t, int row=0);
vector<Recipe> readRecipesFromTable(ResultTable t);
};
#endif // RECIPEDATABASE_H