pub / serci

Search the web with !keywords
git clone https://https://src.jayvii.de/pub/serci.git
Home | Log | Files | Exports | Refs | README | RSS

commit 052f3db6fb4dd42c277ea314fd19677542bfdc77
parent 6570e8771d6e15fcfd07a35621f53c2d498e2795
Author: JayVii <jayvii[AT]posteo[DOT]de>
Date:   Thu, 17 Oct 2024 18:47:30 +0200

feat: redesign webfrontend

Diffstat:
Massets/css/custom.css | 61+++++++++++++++++++++++++++++++++++++++++++++++++++++--------
Mindex.php | 352+++++++++++++++++++++++++++++++++++++++++++++++++++++--------------------------
2 files changed, 290 insertions(+), 123 deletions(-)

diff --git a/assets/css/custom.css b/assets/css/custom.css @@ -3,11 +3,18 @@ * It should flex / share row with the search button */ #searchform { + margin-top: 3em; width: 100%; display: flex; flex-direction: row; } +/* Search bar should stretch across entire content-width */ +#searchbar { + width: 100%; + margin-right: 5px; +} + /* On mobile devices, the search button should be in its own row instead */ @media only screen and (width <= 720px) { #searchform { @@ -15,16 +22,54 @@ } } -/* Search bar should stretch across entire content-width */ -#searchbar { - width: 100%; - margin-right: 5px; +/* Set large margins around the description */ +.description { + margin-top: 3em; + margin-bottom: 50vh; +} + +/* Description buttons should always be in one line */ +.description > .button { + width: calc((100% / 2) - 10px); /* Two buttons with 10px margin between */ + text-align: center; +} + +/* Buttons and Code/Marks within article class should have wider margins */ +button, +.button, +article > code, +article > mark +{ + margin: 3px; } -/* Content within tables should wrap anywhere to fit small screens */ -td { - word-wrap: anywhere; +/* Utility class for hidden content */ +.hidden { + display: none; + visibility: none; } -table, tbody, thead { + +/* Utility function for in-lining content */ +.row { + display: flex; + flex-direction: row; + flex-wrap: wrap; width: 100%; } +@media only screen and (width <= 720px) { + .row { + flex-direction: column; + } +} + +/* Set selection colours for the article class */ +article.selected { + background-color: #00FF0033; +} +article:not(.selected) { + background-color: #FF000033; +} +article:not(.selected) { + cursor: pointer; +} + diff --git a/index.php b/index.php @@ -103,8 +103,24 @@ <!-- Body --> <body> + <!-- Header --> + <header> + <nav> + <a href="#engines"> + Engines + </a> + <a href="#faqs"> + FAQ + </a> + <a href="https://src.jayvii.de/pub/serci/" target="_blank"> + Development + </a> + </nav> + <h1>serĉi</h1> + <p>Search with Keywords</p> + </header> + <!-- Search Bar --> - <h1>serĉi - Search with !keywords</h1> <form id="searchform" action="/" method="get"> <input id="searchbar" @@ -128,148 +144,232 @@ > </form> - <!-- FAQs --> - <h3>FAQs</h3> - <ul> - <li> - <a href="https://src.jayvii.de/pub/serci/#what-does-serĉi-mean" - target="_blank">What does <em>serĉi</em> mean?</a> - </li> - <li> - <a href="https://src.jayvii.de/pub/serci/#what-are-keywords" - target="_blank">What are keywords?</a> - </li> - <li> - <a href="https://src.jayvii.de/pub/serci/#how-can-i-use-serĉi" - target="_blank">How to use serĉi?</a> - </li> - <li> - <a href="https://src.jayvii.de/pub/serci/" - target="_blank">Help with development!</a> - </li> - </ul> + <!-- Description --> + <div class="description"> + <strong style="font-size: 133%;"> + The keyword engine for power users that sits on top of your + favorite search engines! + </strong> + <p> + Have all your favorite search providers right at your finger + tips all the time and use them directly via + <code>!keywords</code> within your search query. + </p> + <a href="#engines" class="button"> + Explore + </a> + <a href="#faqs" class="button"> + Learn more + </a> + </div> <!-- Search Engine Lists --> - <h3>Search Engines</h3> - <p> - Choose your default search: - <select - name="default_search" - id="default_search" - onchange="select_default_searchengine()" - > + <h3 id="engines">Available Search Engines</h3> + + <!-- Search Engine Searchbar --> + <input + id="engines_searchbar" + name="engines" + type="text" + placeholder="Explore the available Search Engines..." + oninput="search_engines('engines_searchbar');" + > + <noscript> + <div class="notice"> + <p> + Exploring the available search engines with the search bar + above as well as choosing your default search engine + requires javascript. However, + <strong>using serĉi itself does not</strong>! + </p> + <p> + Read the <a href="#faqs">FAQs</a> on how to choose a default + search engine when javascript and cookies are disabled. + </p> + </div> + </noscript> + + <!-- Search Engine Category Buttons --> + <details id="categories"> + <summary>Categories</summary> + <div class="row"> <?php - /* Cycle through all available search engines - * Create <option> objects for each one - * Mark the default search engine as "selected" - */ - foreach (array_keys($searches) as $search) { + foreach (array_keys($categories) as $catid) { + $cat_name = $categories[$catid]["name"]; ?> - <option - value="<?php echo $search; ?>" - <?php - if ($search == $default_search) { - echo "selected"; - } - ?> + + <button + onclick="search_for_category('#<?php echo $cat_name; ?>');" > - <?php echo $searches[$search]["name"]; ?> - </option> + <?php echo "#" . $cat_name; ?> + </button> + <?php } ?> - </select> - </p> - - <!-- Toggle-Button --> - <button onclick="toggle_details();"> - Toggle Categories - </button> + </div> + </details> - <!-- Search Engine Categorical Lists --> + <!-- Search Engine List --> <?php - foreach ($searchcats as $category => $searchids) { + foreach (array_keys($searches) as $searchid) { + $search = $searches[$searchid]; ?> - - <details - id="<?php echo $category; ?>" - onclick="scroll_to('<?php echo $category; ?>');" + <article + onclick="make_default('<?php echo $searchid; ?>');" + <?php + echo "id=\"" . $searchid . "\""; + if ($searchid == $default_search) { + echo "class=\"selected\""; + } + ?> > - <summary> - <?php echo $categories[$category]["name"]; ?> - </summary> - <table> - <thead> - <tr> - <th>Engine</th> - <th>keywords</th> - <tr> - </thead> - <tbody> - <?php - /* Print one table row for each search engine in category */ - foreach ($searchids as $searchid) { - ?> - <tr> - <td> - <a href="<?php echo $searches[$searchid]["website"]; ?>" - target="_blank"> - <?php - echo $searches[$searchid]["name"]; - ?> - </a> - </td> - <td> - <code> - <?php - echo "!" . - implode( - "</code>, <code>!", - $searches[$searchid]["keywords"] - ); - ?> - </code> - </td> - </tr> + <h3> + <a href="<?php echo $search["website"]; ?>" target="_blank"> + <?php echo $search["name"]; ?> + </a> + </h3> + <p><?php echo $search["description"]; ?></p> + <?php + foreach ($search["categories"] as $catid) { + $cat_name = $categories[$catid]["name"]; + ?> + <mark><?php echo "#" . $categories[$catid]["name"]; ?></mark> + <?php + } + ?> + <br> + <strong>Keywords: </strong> + <code> <?php - } + echo "!" . + implode( + "</code><code>!", + $search["keywords"] + ); ?> - </tbody> - </table> - </details> + </code> + <p style="font-size: 66%;"> + (click here to choose this as your default search engine. This + will set a cookie!) + </p> + </article> <?php } ?> + <hr> + <h3 id="faqs">About serĉi</h3> + <?php $fsi = array_key_first($searches); /* Used within examples */ ?> + + <h4>What does serĉi mean?</h4> + <p> + It is the Esperanto term for + <a href="https://eneo.dict.cc/?s=ser%C4%89i" target="_blank"> + to search</a>. This may not be the most creative name for such a + software project, but to the best of my knowledge, it is a unique + one. + </p> + + <h4>What are keywords?</h4> + <p> + An idea lent from the search Engine + <a href="https://duckduckgo.com/bangs" target="_blank"> + DuckDuckGo + </a>, which has been utilized by many others since. They call their + keywords bangs, but it is the same concept and usability. In + essence, keywords are shortcuts for searching on other websites. + </p> + <p> + For example, you can conduct a search on the website + <a href="<?php echo $searches[$fsi]["website"]; ?>" target="_blank"> + <?php echo $searches[$fsi]["name"]; ?> + </a> + directly from <?php echo $_SERVER["SERVER_NAME"]; ?> by adding the + keyword <code>!<?php echo $searches[$fsi]["keywords"][0]; ?></code> + to your search query. + </p> + <p> + You can find all keywords associated with each search engine in the + <a href="#engines">list above</a>. + </p> + + <h4>How can I use serĉi?</h4> + <p> + You can try serĉi directly <a href="#searchbar">on this site</a> or + <a href="https://src.jayvii.de/pub/serci" target="_blank"> + host it yourself + </a>! It barely needs any server resources, no database or lots of + RAM. serĉi has minimal footprint (also on user data: there are + <strong>NONE</strong>). + </p> + <p> + Either type your search directly into the + <a href="#searchbar">search bar at the very top</a> + or add the search to your browser by rightclicking in the URL-bar of + your web browser and choose + <emph>add serĉi - Search with !keywords</emph>. + </p> + <p> + Some browsers (for example Firefox on Android / Fennec) allow to + configure custom search engines via a so-called search URL. Simply + list following URL as <emph>search-URL</emph> there and choose it as + your default search option: + </p> + <pre>https://<?php echo $_SERVER["SERVER_NAME"]; ?>/?q=%s</pre> + <p> + You can also choose the default search engine, used by serĉi as + fallback, when no keyword is given, through the URL instead of + choosing it from the <a href="#engines">list above</a>, in case you + do not want serĉi to store any cookie on your device. For example, + if you wanted to use + <a href="<?php echo $searches[$fsi]["website"]; ?>" target="_blank"> + <?php echo $searches[$fsi]["name"]; ?> + </a> + as your default search, you could use following search-URL: + </p> + <pre><?php + echo "https://" . $_SERVER["SERVER_NAME"] . + "/?default_search=" . $fsi . "&q=%s"; + ?></pre> + + <h4>Choosing a default search without cookies or Javascript</h4> + <p> + You can simply choose a default search by adding the + <code>default_search</code> URL parameter. For example, if you + wanted to use + <a href="<?php echo $searches[$fsi]["website"]; ?>" target="_blank"> + <?php echo $searches[$fsi]["name"]; ?> + </a> + as your default search, you can simply add + <code>/?default_search=<?php echo $fsi; ?></code> to the serĉi URL: + <br> + <a href="/?default_search=<?php echo $fsi; ?>"> + <?php + echo "https://" . $_SERVER["SERVER_NAME"] . + "/?default_search=" . $fsi; + ?> + </a> + </p> + </body> <!-- Script for selecting default Search Engine --> <script> - select_default_searchengine = function() { - // Fetch the default search selection - var selections = document.querySelector('#default_search'); - var selection = selections.selectedOptions[0].value; - // Set the expiration time for the cookie (1 year) - const d = new Date(); - d.setTime(d.getTime() + (365*24*60*60*1000)); - let expires = "expires="+ d.toUTCString(); + make_default = function(selection) { // Set a cookie for the selection document.cookie = "default_search=" + selection + ";" + "Max-Age=31536000;" + // 60 x 60 x 24 x 365 = 1 year "Domain=" + document.domain + ";" + "SameSite=Strict;"; - } - </script> - - <!-- Script for toggling Search Engine tables --> - <script> - toggle_details = function() { - var setas = (1 - document.querySelector('details').open); - document.querySelectorAll('details').forEach( - function(d) { - d.open = setas; + var entries = document.querySelectorAll("article") + for (let i = 0; i < entries.length; i++) { + if (entries[i].id == selection) { + entries[i].classList.add("selected"); + } else { + entries[i].classList.remove("selected"); } - ); + } } </script> @@ -291,5 +391,27 @@ } </script> + <script> + search_engines = function(bar) { + var pat = document.getElementById(bar).value.toLowerCase(); + var entries = document.querySelectorAll("article") + for (let i = 0; i < entries.length; i++) { + if ( + entries[i].innerText.toLowerCase().match(pat) === null + ) { + entries[i].classList.add("hidden"); + } else { + entries[i].classList.remove("hidden"); + } + } + setTimeout(scroll_to("engines"), 500); + } + search_for_category = function(category) { + document.getElementById("engines_searchbar").value = category; + document.getElementById("categories").open = false; + setTimeout(search_engines("engines_searchbar"), 500); + } + </script> + </html>