Jump to content

Stefanowitsch

Members
  • Posts

    412
  • Joined

  • Last visited

  • Days Won

    7

Everything posted by Stefanowitsch

  1. I have installed the module. On the module settings page in the "Add fields to template" checkbox-list some of my templates are missing (where I need to add the field). Does the module kind of "sort out" some templates depending on the settings here? Am I able to add the required fields "by hand" in the template settings instead?
  2. Thanks for testing! I only have my iPhone for testing and there the behaviour is identical in safari + chrome. I asked the same question on the UIKit discord channel yesterday. Which is a bit new for me - describing such a complicated thing in a chat room environment. Maybe they have an explanation.
  3. I ran over a bug (?) that kind of freaks me out. It's this kind of problem that seems to occur without any reason. But let me explain: I have a project that is using the latest UIKit 3 library. On the homepage I make use of a slideshow component which is also configured to take space of the entire viewport height (via: uk-height-viewport). The other content elements are introduced by using the Scrollspy component when scrolling down. I was wondering why no link is working (even javascript on click events on anything on the page). Instead the "first" click only triggers the hover state of the link/button. Then the second click triggers the link event. This only occurs on mobile devices (like my iPhone). The only solution to make links work in the first place is to get rid of the uk-height-viewport attribute of the slideshow. OR to get rid of all the Scrollspy instances. This makes no sense to me. I made a small demo site where I can exactly reproduce this phenomenon. So it seems to have nothing to to with my project code but is in fact a kind of UIKit bug (?). Please have a look: http://uikit.thumann-preview.de/ 1. Open the page on a mobile device 2. Scroll down to the red button 3. Tap on the button. Nothing happens but the hover state is activated. 4. Tap again on the button. The link is working. I also made a short video that shows the problem: RPReplay_Final1675711729.MP4 Here's the code of this test page: <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>CDN Example</title> <script src="https://cdnjs.cloudflare.com/ajax/libs/uikit/3.15.11/js/uikit.min.js" integrity="sha512-uNdy6/b4kpAKQgC1MqDRW7HzGqmja6jPPfQ0Pv3q4f0r5XpL4cxPlgqgSbFT5pnLFo4BSFZX8Ve/ak0DDN06OA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/uikit/3.15.11/css/uikit-core-rtl.min.css" integrity="sha512-+6D4TOLdOBhkuufbELpbCiGmD+Y4dzrNbSPGwtgGO2nf7Id3dM0x5R/Cw0bI/13pFUnsRL8pfpmKNWLbAx8fGg==" crossorigin="anonymous" referrerpolicy="no-referrer" /> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/uikit/3.15.11/css/uikit-core.min.css" integrity="sha512-Up68klxaLGLgBXFtu9KAkcM0/b1Vv97wru/VabGokNEwbQN1RBjBtthqDgildf/8YCOKaaLvT5ZfIvVPom5dIw==" crossorigin="anonymous" referrerpolicy="no-referrer" /> <script src="https://cdnjs.cloudflare.com/ajax/libs/uikit/3.15.11/js/uikit-icons.min.js" integrity="sha512-Rrh7aqdTz7Q1BPfCdWCK3poag9FNK1HQJMbSdL/eRZwXkbS1EWlY5n2XJ70ZVh1ZLRIJEUoWxATps1cyzpGp/g==" crossorigin="anonymous" referrerpolicy="no-referrer"></script> <style> body { max-width: 90%; margin: auto; background-color: rgb(227, 227, 227); } footer { padding: 10px; background-color: cornflowerblue; padding-top: 20px; } </style> </head> <body> <header> <nav class="uk-navbar-container" uk-navbar style="background-color: cornflowerblue;"> <div class="uk-navbar-right"> <ul class="uk-navbar-nav"> <li class="uk-active"><a href="#" style="color: white">Home</a></li> <li> <a href="#" style="color: white">Account</a> <div class="uk-navbar-dropdown"> <ul class="uk-nav uk-navbar-dropdown-nav"> <li class="uk-active"><a href="#">Login</a></li> <li><a href="#">Sign Up</a></li> <li><a href="#">Report</a></li> </ul> </div> </li> <li><a href="#" style="color: white">Item</a></li> </ul> </div> </nav> </header> <!-- Slider --> <div class="uk-position-relative uk-visible-toggle uk-light" tabindex="-1" uk-slideshow="ratio: false"> <ul class="uk-slideshow-items" uk-height-viewport> <li> <img src="https://picsum.photos/200/400" alt="" uk-cover> </li> </ul> <a class="uk-position-center-left uk-position-small uk-hidden-hover" href="#" uk-slidenav-previous uk-slideshow-item="previous"></a> <a class="uk-position-center-right uk-position-small uk-hidden-hover" href="#" uk-slidenav-next uk-slideshow-item="next"></a> </div> <!-- Cenetred Text --> <h1 class="uk-text-primary uk-text-center">This is awesome</h1> <!-- Adding card --> <div class="uk-child-width-1-3@m uk-grid-small uk-grid-match" uk-grid uk-scrollspy="cls: uk-animation-slide-bottom"> <div> <div class="uk-card uk-card-primary uk-card-body"> <h3 class="uk-card-title">Card1</h3> <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</p> </div> </div> <div> <div class="uk-card uk-card-warning uk-card-body"> <h3 class="uk-card-title">Card 2</h3> <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</p> </div> </div> <div> <div class="uk-card uk-card-secondary uk-card-body"> <h3 class="uk-card-title">Card 3</h3> <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</p> </div> </div> </div> <div class="uk-child-width-1-3@m uk-grid-small uk-grid-match" uk-grid uk-scrollspy="cls: uk-animation-slide-bottom"> <div> <div class="uk-card uk-card-warning uk-card-body"> <h3 class="uk-card-title">Card 4</h3> <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</p> </div> </div> <div> <div class="uk-card uk-card-secondary uk-card-body"> <h3 class="uk-card-title">Card5</h3> <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</p> </div> </div> <div> <div class="uk-card uk-card-primary uk-card-body"> <h3 class="uk-card-title">Card 6</h3> <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</p> </div> </div> </div> <a href="https://www.google.de" class="uk-button uk-button-danger uk-margin">I AM NOT WORKING :-(</a> <!-- Card with images --> <div class="uk-child-width-1-2@m" uk-grid uk-scrollspy="cls: uk-animation-slide-bottom"> <div> <div class="uk-card uk-card-default"> <div class="uk-card-media-top"> <img src="/slides/slide3.png" width="1800" height="1200" alt=""> </div> <div class="uk-card-body"> <h3 class="uk-card-title">Human</h3> <p>An average of 20 times every minute, your eyes blink. The tongue has roughly 8,000 taste buds, each of which can have up to 100 cells. In reality, earwax is a form of sweat.</p> </div> </div> </div> <div> <div class="uk-card uk-card-default"> <div class="uk-card-body"> <h3 class="uk-card-title">Cat</h3> <p>Cats have a 6-times-their-height jump capacity. The average cat snoozes for 13 to 16 hours every day (roughly 70% of their life). A cat's lifespan is equivalent to 15 years in a person's life. A Maine Coon is one of the largest domestic cat breeds.</p> </div> <div class="uk-card-media-bottom"> <img src="/slides//slide4.png" width="1800" height="1200" alt=""> </div> </div> </div> </div> <br> <br> </body> </html>
  4. Yeah thats what I needed to know. I look for a way to insert a simple <span> around a word or phrase inside the headline. I can then style this <span> like I want (color, different font, etc.) So I can just add this option here I guess (I used the @ as an example) ? @i have span around@ $str = preg_replace("/$start@(.*?)@$end/", "$1<span>$2</span>$3", $str);
  5. Interesting. I have those "Headlines with bold/italic Text inside" in nearly all projects. I used to solve this by using a CKEditor for the Headline. Which is a bit over the top for a single headline that can (and should?) be handled in a text field: How does the formatted text element look inside the HTML code? Does your module apply the <i></i> or <b></b> tags dynamically? Is it possible to define custom formatting options for example a colored word inside a headline phrase (see screenshot). Last but not least: I never used a Textformatter before. How and where do I apply the Formatter to my field?
  6. SOLVED: THE FIELD HAS TO BE SET AS A MANDATORY FIELD (=REQUIRED) TO DISPLAY THE DEFAULT VALUE... This is the first time that I want to make use of a select field with a default value. It's all about the position of an image in this case. Either left or right. I want do have "left" as default value. So here are my field settings: This is how it looks on the page I am editing: The default value is never set. What am I doing wrong?
  7. I PHP 8.1 required? My projects run on PHP 8, because of several modules that do not work with 8.1 (yet!).
  8. That would be nice too. I am using UIKit and the sticky navbar has a default z-index of 980.
  9. Aaaah! I have a fixed navbar in my project which acts as an overlay. So your topbar was hidden underneath it. My only advise would be to increase the z-index of the topbar to a really high value to make sure it will be visible in most of the cases. I love the mobile toggle option. It would be nice to be able to chose between tablet and phone size.
  10. I saw this new "Topbar" Checkbox in the settings. What exactly does this do? When checked I expected some kind of new element floating in the frontend but I didn't see anything ?
  11. Cool! I've been searching for a module like this. This comes in handy when users are preparing blog/news articles and want them to be published automatically on a specific date. I will definitely try it out.
  12. Hello and welcome to ProcessWire! Basically what we are talking about here is called a "multi site". This article here explains some options how to achieve this: https://processwire.com/docs/more/multi-site-support/ When your two websites differ very much design wise and from the template/field structure I would not use the multi-site module (option #2) but instead install two separate PW instances to keep it cleaner.
  13. No pain! Its just a question of the workflow. At some point or another you would have to do all things from the migrate.php instead of going through Setup->Fields->Add. It's just different way of approaching things... how can I describe it... it's like a more professional, developer-style approach. I personally am a fan of frontend editing, where you can see what you do and where you click. Sometimes this is safer to use but none the less it will slow you down after time. What I like about RM is that it only takes a few moments to do lots of things once you are familiar the RM syntax. But at first it will resolve in a bit of trial and error and some people (including me) might be afraid to start using it in a finished and complex project. That does not mean that I never want to use RM. The opposite: Your recent video here answered a few of my questions I had before so now I want to try a few things out.
  14. +1 ! That is the main reason why I am too afraid / too busy to start using rock migrations right now. I understand that in the end it can save you a lot of time but you have to start somewhere and it seems that all the field administration/creation will be done from the migrate.php instead of clicking around in the backend (the normal way) from then on. I mean the typical use case for me would be the following scenario: During site development I do all my field/template creation and settings in the backend. Adding fields to templates, edit the field in template context, etc. etc. Then the site goes live. THEN the client wants something new on the site or wants to change things. This is the moment where PW development becomes a little painful. You have to alter fields or add some new on your local dev environment and test it. Then you have to make all those changes on the live site again. You COULD however replace the database on the server (which includes all the new stuff) but what if other changes were made in the meantime on the live site? Like new articles, new subpages...
  15. I am doing the exact thing in a project and this is how I get those events: // all future events from "today" $events = $page->children("date_event>=today, sort=date_event, sort=time_from, limit=6"); The magic lies here. You can literally "tell" the selector what to do. You don't need any timestamps or date functions. date_event>=today You could also do things like: // get all events of the current year $events = $pages->find("template=event, date_event>='first day of this year', date_event<'last day of this year', sort=date_event, sort=time_from, limit=6");
  16. After upgrading to PHP 8.1 I get this message when sending mail: Deprecated: Function strftime() is deprecated in /Users/XXX/Sites/processwire-ui3/site/assets/cache/FileCompiler/site/modules/WireMailSmtp/smtp_classes/email_message.php on line 675 This is no surprise - strftime() needs to be replaced in the future. It's still working fine at the moment, though. See email_message.php, Line 675: return($this->FormatHeader("Message-ID", "<".strftime("%Y%m%d%H%M%S", $seconds).substr($micros,1,5).".".preg_replace('/[^A-Za-z]/', '-', $local)."@".preg_replace('/[^.A-Za-z_-]/', '', $host).">")); I am afraid to fix this line by myself... it looks complicated ?
  17. Yes absolutely. I have this kind of monstrosities in my markup: <?= IntlDateFormatter::formatObject( new DateTime(date("d.m.Y", $event->date_event)), "EEEE, dd.MM.yy", 'de_DE' ); ?> Which works perfect but is a bit hard to read and to maintain (in fact I never want to touch this code again...). If you are working with a predefined date format all over your site it really makes sense to preconfig that.
  18. I agree, you have to use the IntDateFormatter class, like @Jan Romero mentioned. Have a look at this thread, I made a few examples how to use the IntDateFormatter as one-liner, etc.
  19. This is great. I am just about to finish a project that deals with events. I will give it a try.
  20. Oh I forgot to mention you for giving me help on this one ? For all that that were not involved in the discussion here and to clear things up: The Google Maps API is in fact not for free. Depending how much API requests (and what kind of API requests) you send, you will have to pay for it. Google offers everyone a monthly discount of 200$. This discount should fit for most of the requests of a small website, so you never have to pay for anything as long as you are below this 200 $ Mark. There is also a nice calculator here: https://mapsplatform.google.com/intl/de/pricing/ If you just receive data over the place details API (which is the API the module uses) you have about 12.000 requests "for free". So I came up with a save function for the request. You can just fetch it once - save it - and don't have to use the API on each request form there on. But that would violate the Google Maps terms. Sadly I had to remove this save function from the module ?
  21. Update: I finally released the module. Feel free to test it and give me some feedback: I scrapped the idea of saving the review data for any purpose. I contacted the google support with this question and they confirmed that it would violate their terms to save this data in any way.
  22. I am proud to announce my very first module: GooglePlaceDetails. I was in the need to include some google place reviews for a clients website. It turned out that no such review widget was available for ProcessWire. So I made my own solution which i want to share with you. Google Place Details for ProcessWire Modules Directory: https://processwire.com/modules/google-place-details/ Github: https://github.com/StefanThumann/GooglePlaceDetails What it does Google Place Details offers the possibility to send requests to the Google Maps API to receive information about a certain place. A typical use case would be to display the reviews of a place on your website. But you can receive any other information that the API offers. Before you start You need three things: A Google API Key The Place ID A project with a billing account activated You can set up all of those by using Googles quick start widget here: https://developers.google.com/maps/third-party-platforms/quick-start-widget-users How to install Copy this directory to /site/modules In your admin, go to Modules > Refresh, then Modules > New Click the "Install" button next to the Google Place Details module Fill out the API Key and Place ID fields in the module settings and you are ready to go. Module settings and field descriptions API Key This field is required and must contain your generated Google API key. Place ID This field is required. You can put the ID of any place into this field. Fields to include in request Specify a comma-separated list of place data types to return. Leave empty to load all default fields. For an overview of the available fields see: https://developers.google.com/maps/documentation/places/web-service/details Review Sorting Chose your sorting criteria. "Most relevant" is used by default. Preview Place Details If checked the place details can be previewed for debugging/development purpose on module page submit. Usage example Load the module in a page context: $module = $modules->get('GooglePlaceDetails'); Call a function to load data $module->getPlaceDetails(); This function fetches the data in realtime, on every page request and returns a php array containing the full response from the Google server. See the frontend example at the end of this document to see how to extract data from the array in a working example. Place details answer example The place details answer will be in JSON format and looks like this (depending of the fields you included in your request) { "html_attributions": [], "result": { "name": "Google Workplace 6", "rating": 4, "reviews": [ { "author_name": "Luke Archibald", "author_url": "https://www.google.com/maps/contrib/113389359827989670652/reviews", "language": "en", "profile_photo_url": "https://lh3.googleusercontent.com/a-/AOh14GhGGmTmvtD34HiRgwHdXVJUTzVbxpsk5_JnNKM5MA=s128-c0x00000000-cc-rp-mo", "rating": 1, "relative_time_description": "a week ago", "text": "Called regarding paid advertising google pages to the top of its site of a scam furniture website misleading and taking peoples money without ever sending a product - explained the situation, explained I'd spoken to an ombudsman regarding it. Listed ticket numbers etc.\n\nThey left the advertisement running.", "time": 1652286798, }, { "author_name": "Tevita Taufoou", "author_url": "https://www.google.com/maps/contrib/105937236918123663309/reviews", "language": "en", "profile_photo_url": "https://lh3.googleusercontent.com/a/AATXAJwZANdRSSg96QeZG--6BazG5uv_BJMIvpZGqwSz=s128-c0x00000000-cc-rp-mo", "rating": 1, "relative_time_description": "6 months ago", "text": "I need help. Google Australia is taking my money. Money I don't have any I am having trouble sorting this issue out", "time": 1637215605, }, { "author_name": "Jordy Baker", "author_url": "https://www.google.com/maps/contrib/102582237417399865640/reviews", "language": "en", "profile_photo_url": "https://lh3.googleusercontent.com/a/AATXAJwgg1tM4aVA4nJCMjlfJtHtFZuxF475Vb6tT74S=s128-c0x00000000-cc-rp-mo", "rating": 1, "relative_time_description": "4 months ago", "text": "I have literally never been here in my life, I am 17 and they are taking money I don't have for no reason.\n\nThis is not ok. I have rent to pay and my own expenses to deal with and now this.", "time": 1641389490, }, { "author_name": "Prem Rathod", "author_url": "https://www.google.com/maps/contrib/115981614018592114142/reviews", "language": "en", "profile_photo_url": "https://lh3.googleusercontent.com/a/AATXAJyEQpqs4YvPPzMPG2dnnRTFPC4jxJfn8YXnm2gz=s128-c0x00000000-cc-rp-mo", "rating": 1, "relative_time_description": "4 months ago", "text": "Terrible service. all reviews are fake and irrelevant. This is about reviewing google as business not the building/staff etc.", "time": 1640159655, }, { "author_name": "Husuni Hamza", "author_url": "https://www.google.com/maps/contrib/102167316656574288776/reviews", "language": "en", "profile_photo_url": "https://lh3.googleusercontent.com/a/AATXAJwRkyvoSlgd06ahkF9XI9D39o6Zc_Oycm5EKuRg=s128-c0x00000000-cc-rp-mo", "rating": 5, "relative_time_description": "7 months ago", "text": "Nice site. Please I want to work with you. Am Alhassan Haruna, from Ghana. Contact me +233553851616", "time": 1633197305, }, ], "url": "https://maps.google.com/?cid=10281119596374313554", "user_ratings_total": 939, "website": "http://google.com/", }, "status": "OK", } Usage in frontend example To display the reviews of a place you can do it like this (very basic markup!). I encourage every user to build their own markup of the reviews, fitting their design. <?php // 1. Connect to module $module = $modules->get('GooglePlaceDetails'); // 2. Save the details array to a variable $details = $module->getPlaceDetails(); // 3. Extract the data you want to iterate over $reviews = $details['result']['reviews']; // For debug purpose dump the array to inspect the data // TRACY DEBUGGER MODULE REQUIRED // dump($reviews); <? foreach ($reviews as $review) { ?> <div> <img src="<?=$review["profile_photo_url"]?>"/> <h4><?=$review["author_name"]?></h4> <? for ($i = 1; $i <= ($review['rating']); $i++) { ?> &#9733; <? } ?> <p><?=$review["text"]?></p> </div> <? } ?> ?> Here is a more advanced and nicer looking version (UIKit 3 Framework Markup is used) <div class="uk-container"> <div uk-slider> <div class="uk-position-relative"> <div class="uk-slider-container"> <ul class="uk-slider-items uk-child-width-1-2@s uk-child-width-1-3@m uk-grid uk-height-medium"> <? foreach ($reviews as $review) { ?> <li> <div class="uk-card uk-card-default uk-card-body"> <div> <img src="<?=$review["profile_photo_url"]?>" class="uk-responsive-width" style="height: 30px;" /> <span class="uk-text-middle"><?=$review["author_name"]?></span> </div> <div class="uk-margin"> <? for ($i = 1; $i <= ($review['rating']); $i++) { ?> &#9733; <? } ?> <? for ($i = 1; $i <= 5 - ($review['rating']); $i++) { ?> &#9734; <? } ?> </div> <div uk-overflow-auto="selContainer: .uk-slider-items; selContent: .uk-card"> <p><?=$review["text"]?></p> </div> </div> </li> <? } ?> </ul> </div> <a class="uk-position-center-left-out uk-position-small" href="#" uk-slidenav-previous uk-slider-item="previous"></a> <a class="uk-position-center-right-out uk-position-small" href="#" uk-slidenav-next uk-slider-item="next"></a> </div> </div> </div> If you are already using UIKit 3 and just want to get a quick result I put the code example above in a function that can can be called like this: <? $module = $modules->get('GooglePlaceDetails'); echo $module->getUIKitMarkupExample(); ?> The template file which is used for the markup lies inside the module directory. Adjust it to your needs.
  23. Long story short: When using the module all requests come directly over the Google Maps API. Every user has to generate an own and unique Google API Key and also activate a billing account. Otherwise no data will be send by Google. This is the only way to receive data over the Google API. In fact you pay for the data you are receiving. Would be a bummer if you are not allowed to store that data for your own usage.
  24. Greetings, everyone! I want to tell you that the module is finished. I have one little concern, though: I planned to in include a save and preview function of the received data for debugging/development purpose. However this would violate the terms of the google maps platform as it seems: https://cloud.google.com/maps-platform/terms 3.2.3 Restrictions Against Misusing the Services. (a) No Scraping. Customer will not export, extract, or otherwise scrape Google Maps Content for use outside the Services. For example, Customer will not: (i) pre-fetch, index, store, reshare, or rehost Google Maps Content outside the services; (ii) bulk download Google Maps tiles, Street View images, geocodes, directions, distance matrix results, roads information, places information, elevation values, and time zone details; (iii) copy and save business names, addresses, or user reviews; or (iv) use Google Maps Content with text-to-speech services. (b) No Caching. Customer will not cache Google Maps Content except as expressly permitted under the Maps Service Specific Terms. (c) No Creating Content From Google Maps Content. Customer will not create content based on Google Maps Content. For example, Customer will not: (i) trace or digitize roadways, building outlines, utility posts, or electrical lines from the Maps JavaScript API Satellite base map type; (ii) create 3D building models from 45° Imagery from Maps JavaScript API; (iii) build terrain models based on elevation values from the Elevation API; (iv) use latitude/longitude values from the Places API as an input for point-in-polygon analysis; (v) construct an index of tree locations within a city from Street View imagery; or (vi) convert text-based driving times into synthesized speech results. This also means that all the review scraper tools out there and the other strategies that we discussed here (fetch the reviews manually and save as page) are also not what google wants us to do. What do you think about that?
  25. It is happening ? but I will need a few more days...
×
×
  • Create New...