diff --git a/README.md b/README.md index 31d5328..b516df9 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,14 @@ # SOUP-GEN 🍜 -A web-to-print cookbook with a collaborative attitude and generative outputs +A web-to-print cookbook with a collaborative attitude and generative outputs. +For now you can add a recipe only if you are from XPUB, but we are working to make this open access. + +To add a recipe: + +1. Enter your Jupiter, and go to `~/shared/html/soup-gen/` +2. Open the notebook `add_recipe.ipynb` +3. Run the first snippet, it will ask you for some info about the recipe: fill the blank space in the + output message. +4. Run the second snippet, it will save the recipe in the Soupboat. +5. You added a recipe! +6. **\_\_CONGRATS\_\_** diff --git a/cms.js b/cms.js index 8d24c56..8965ff0 100644 --- a/cms.js +++ b/cms.js @@ -1,6 +1,14 @@ const cookbook = document.getElementById("cookbook"); const cookbookInfo = document.getElementById("cookbookInfo"); +const ingredientsContainer = document.getElementById("ingredients-container"); +const activeAllButton = document.getElementById("active-all"); + +let selectedIngredients = new Set(); +let ingredientsList = []; // list of unique ingredients +let tagList; +let recipesList; + fetch("./cms.json") .then((response) => { return response.json(); @@ -8,10 +16,14 @@ fetch("./cms.json") .then((data) => { populateContents(data); recipesInfo(data.recipes); + ingredientsTag(); + showAllTags(); + showSelectedRecipes(); }); function populateContents(data) { data.recipes.forEach((recipe) => addRecipe(recipe)); + recipesList = [...document.getElementsByClassName("recipe")]; } function addRecipe(recipe) { @@ -51,6 +63,8 @@ function addRecipe(recipe) { let ingredient = document.createElement("li"); ingredient.innerHTML = item; ingredientsList.appendChild(ingredient); + item = item.replaceAll(" ", "-"); + card.classList.add(item); }); ingredients.appendChild(ingredientsList); card.appendChild(ingredients); @@ -79,6 +93,111 @@ function recipesInfo(recipes) { let ingredients = []; recipes.forEach((recipe) => (ingredients = [...ingredients, ...recipe.ingredients])); let unique = [...new Set(ingredients)]; + ingredientsList = Array.from(unique); cookbookInfo.innerHTML = `There are ${recipes.length} recipes in the cookbook, with a total of ${unique.length} different ingredients`; } + +// Create tags from the ingredients list of the recipes +function ingredientsTag() { + ingredientsList.forEach((ingredient) => { + let tag = document.createElement("li"); + tag.classList.add("tag"); + tag.setAttribute("data-tag", ingredient); + tag.setAttribute("tabindex", 0); + tag.innerHTML = ingredient; + ingredientsContainer.appendChild(tag); + }); + tagList = document.querySelectorAll("[data-tag]"); +} + +let allActive = true; + +function conditionalToggle(element) { + if (allActive) { + tagList.forEach((tag) => { + selectedIngredients.delete(tag.getAttribute("data-tag")); + tag.classList.remove("active"); + tag.setAttribute("aria-expanded", "false"); + }); + activeAllButton.classList.remove("active"); + allActive = false; + } + + // conditional toggle ecc + if (element.classList.contains("active")) { + element.classList.remove("active"); + element.setAttribute("aria-expanded", "false"); + selectedIngredients.delete(element.getAttribute("data-tag")); + } else { + element.classList.add("active"); + element.setAttribute("aria-expanded", "true"); + selectedIngredients.add(element.getAttribute("data-tag")); + } + + // final check + + allActive = tagList.length == selectedIngredients.size; + + if (allActive) { + activeAllButton.classList.add("active"); + activeAllButton.setAttribute("aria-expanded", "true"); + } +} + +function showAllTags() { + tagList.forEach((tag) => { + selectedIngredients.add(tag.getAttribute("data-tag")); + tag.classList.add("active"); + tag.setAttribute("aria-expanded", "true"); + }); + allActive = true; + showSelectedRecipes(); +} + +function showSelectedRecipes() { + recipesList.forEach((recipe) => { + recipe.classList.remove("active"); + }); + + selectedIngredients.forEach((ingredient) => { + //filter function + let selectedRecipes = recipesList.filter((el) => { + ingredient = ingredient.replaceAll(" ", "-"); + return el.classList.contains(ingredient); + }); + selectedRecipes.forEach((recipe) => { + recipe.classList.add("active"); + }); + }); + + allActiveCheck(); +} + +function allActiveCheck() { + if (tagList.length === selectedIngredients.size) { + allActive = true; + tagList.forEach((tag) => tag.classList.add("all")); + // categoriesContainer.firstElementChild.classList.add("active"); + } else { + allActive = false; + tagList.forEach((tag) => tag.classList.remove("all")); + // categoriesContainer.firstElementChild.classList.remove("active"); + } +} + +// Event Listeners + +ingredientsContainer.addEventListener("click", (e) => { + //if click is on a tag/LIst element, then execute conditional toggle + if (e.target.tagName === "LI") { + conditionalToggle(e.target); + showSelectedRecipes(); + } +}); + +activeAllButton.addEventListener("click", (e) => { + activeAllButton.classList.add("active"); + activeAllButton.setAttribute("aria-expanded", "true"); + showAllTags(); +}); diff --git a/cms.json b/cms.json index 0f8f190..20ef321 100644 --- a/cms.json +++ b/cms.json @@ -1 +1 @@ -{"recipes": [{"title": "Pizza and fruit salad soup", "description": "Minim laborum ipsum sunt minim nulla officia cillum quis labore ad voluptate enim deserunt nulla.", "chef": "chef Malvozzo", "ingredients": ["\ud83c\udf55", "\ud83e\udd6d", "\ud83c\udf49", "\ud83c\udf48"], "instructions": ["Id est velit ullamco ea sint aliqua laboris incididunt consectetur do aliqua sint eiusmod.", "Mescola", "Pariatur eu exercitation ipsum qui e", "Quis pariatur magna id pariatur consectetur irure in sint.", "Culpa sunt non consequat consequat excepteur amet ut veniam cupidatat in occaecat consectetur velit.", "servire ben caldo!"]}, {"title": "Kip & Ice Kream Siup", "description": "Id consequat deserunt laborum ea commodo sit voluptate sunt commodo excepteur sit incididunt amet.", "chef": "Mad Moonfish", "ingredients": ["\ud83c\udf57", "\ud83c\udf5a", "funghetti", "\ud83c\udf49", "\ud83e\udd57"], "instructions": ["Exercitation eiusmod adipisicing ex ut amet qui minim est anim reprehenderit nulla voluptate quis.", "Occaecat anim veniam occaecat ut pariatur culpa sit reprehenderit ullamco cupidatat.", "Et reprehenderit mollit cillum Lorem est.", "Magna aliquip sint aliqua proident.", "sluuuurp"]}, {"title": "NLTK Soupa", "description": "A delicious soup made with natural language tomato and kiwi", "chef": "Python", "ingredients": ["pasta", "mushroom", "pizza", "internet"], "instructions": ["Cook the pasta in the internet", "Dig a hole near a mushroom", "Bury the pizza in the hole", "Turn off internet", "Drain the pasta", "Turn internet on again"]}, {"title": "A new sup", "description": "just a test soup to see how does the cms taste like", "chef": "python", "ingredients": ["computer", "soupboat", "jupiter", "zen"], "instructions": ["turn on the computer", "enter the soupboat", "access jupiter", "start the kernel with little zen", "put python to boil", "wait and shift enter"]}, {"title": "Misu sup", "description": "A tasty misu sup yes yes yes", "chef": "Mitsos", "ingredients": ["Miso", "Water", "Salt", "Hash", "Egg", "Oil", "Pepper", "Glitter", "Mushrooms"], "instructions": ["Take the glitter and put them on your face", "Boil the water", "Throw the mushrooms in the boiling water", "Throw an egg against your neighbour", "Add salt and pepper", "Enjoy"]}, {"title": "A visual studio soup", "description": "A soup from the jupiter lab in visual studio ecc ecc really testy", "chef": "Visual sudo", "ingredients": ["Visual Studio", "Zen", "soup-gen repo", "git", "soupboat"], "instructions": ["Open visual studio and pull the repo from git", "Follow the jupiter notebook", "hope it works", "commit and push all the changes", "update the soupboat"]}]} \ No newline at end of file +{"recipes": [{"title": "Pizza and fruit salad soup", "description": "Minim laborum ipsum sunt minim nulla officia cillum quis labore ad voluptate enim deserunt nulla.", "chef": "chef Malvozzo", "ingredients": ["\ud83c\udf55", "\ud83e\udd6d", "\ud83c\udf49", "\ud83c\udf48"], "instructions": ["Id est velit ullamco ea sint aliqua laboris incididunt consectetur do aliqua sint eiusmod.", "Mescola", "Pariatur eu exercitation ipsum qui e", "Quis pariatur magna id pariatur consectetur irure in sint.", "Culpa sunt non consequat consequat excepteur amet ut veniam cupidatat in occaecat consectetur velit.", "servire ben caldo!"]}, {"title": "Kip & Ice Kream Siup", "description": "Id consequat deserunt laborum ea commodo sit voluptate sunt commodo excepteur sit incididunt amet.", "chef": "Mad Moonfish", "ingredients": ["\ud83c\udf57", "\ud83c\udf5a", "funghetti", "\ud83c\udf49", "\ud83e\udd57"], "instructions": ["Exercitation eiusmod adipisicing ex ut amet qui minim est anim reprehenderit nulla voluptate quis.", "Occaecat anim veniam occaecat ut pariatur culpa sit reprehenderit ullamco cupidatat.", "Et reprehenderit mollit cillum Lorem est.", "Magna aliquip sint aliqua proident.", "sluuuurp"]}, {"title": "NLTK Soupa", "description": "A delicious soup made with natural language tomato and kiwi", "chef": "Python", "ingredients": ["pasta", "Mushrooms", "pizza", "internet"], "instructions": ["Cook the pasta in the internet", "Dig a hole near a Mushrooms", "Bury the pizza in the hole", "Turn off internet", "Drain the pasta", "Turn internet on again"]}, {"title": "A new sup", "description": "just a test soup to see how does the cms taste like", "chef": "python", "ingredients": ["computer", "soupboat", "jupiter", "zen"], "instructions": ["turn on the computer", "enter the soupboat", "access jupiter", "start the kernel with little zen", "put python to boil", "wait and shift enter"]}, {"title": "Misu sup", "description": "A tasty misu sup yes yes yes", "chef": "Mitsos", "ingredients": ["Miso", "Water", "Salt", "Hash", "Egg", "Oil", "Pepper", "Glitter", "Mushrooms"], "instructions": ["Take the glitter and put them on your face", "Boil the water", "Throw the mushrooms in the boiling water", "Throw an egg against your neighbour", "Add salt and pepper", "Enjoy"]}, {"title": "A visual studio soup", "description": "A soup from the jupiter lab in visual studio ecc ecc really testy", "chef": "Visual sudo", "ingredients": ["Visual Studio", "Zen", "soup-gen repo", "git", "soupboat"], "instructions": ["Open visual studio and pull the repo from git", "Follow the jupiter notebook", "hope it works", "commit and push all the changes", "update the soupboat"]}]} \ No newline at end of file diff --git a/index.html b/index.html index 1ace8c2..bfbd24c 100644 --- a/index.html +++ b/index.html @@ -47,7 +47,7 @@ Each soup has: -
+

Title

Description
@@ -76,6 +76,9 @@

Soup Gen Cookbook

+
    + +
@@ -83,11 +86,12 @@
    TODO short term: -
  • 💻 Receive recipe as a form ?
  • -
  • 🔍 Ingredients list and filter!!! (like chat reader)
  • +
  • 🔍 Ingredients list and filter!!! (like chat reader)
  • +
  • 🚫 Inclusive / Exclusive filters
  • 💬 Different types of entries for the cms: recipe, diary, ecc.
  • -
  • 📷 Add recipe picture ?
  • 🎨 Design
  • +
  • 💻 Receive recipe as a form ?
  • +
  • 📷 Add recipe picture ?
  • TODO long term:
  • 💾 Better CMS (and not just a JSON file ah ah)
  • @@ -100,6 +104,7 @@
      Questions: +
    • What is the best solution to receive recipes from users??? We imagine it to be something like an HTML form that the NGNIX server could parse and then put in diff --git a/style.css b/style.css index 84ac9fb..0ccda0d 100644 --- a/style.css +++ b/style.css @@ -13,8 +13,6 @@ body { border: 1px solid currentColor; } - - h1, h2, h3 { @@ -27,6 +25,10 @@ ol { list-style-position: inside; } +ul { + list-style: none; +} + em { display: block; margin-top: 1.6em; @@ -62,6 +64,23 @@ em { font-style: italic; } +.tag, +button.tag { + background-color: transparent; + font-size: 20px; + display: inline-block; + border: 1px solid currentColor; + padding: 0 0.5ch; + border-radius: 1em; + margin: 4px; + text-transform: capitalize; + user-select: none; +} + +.tag.active { + background-color: white; +} + .recipes { display: flex; justify-content: flex-start; @@ -72,8 +91,9 @@ em { column-gap: 16px; } -.recipe { - display: inline-block; +.recipe, +.recipe-info { + display: none; background-color: #ffffff; flex-grow: 1; flex-basis: 55ch; @@ -82,6 +102,16 @@ em { padding: 1ch; } +.recipe.active { + display: inline-block; +} + +.recipe-info { + display: inline-block; + border: 1px solid currentColor; + margin: 16px 0; +} + .recipe .title { margin-bottom: 8px; } @@ -123,3 +153,8 @@ em { .intro .recipe { margin: 16px 0; } + +.done { + text-decoration: line-through; + opacity: 0.75; +}