Jump to content

Leaderboard

Popular Content

Showing content with the highest reputation on 08/22/2016 in all areas

  1. If you want to learn I'd highly suggest subscribing to laracasts. While the main focus is obviously laravel it does also have tons of general php videos from beginner to advanced levels. I've learned so much there – even from some of the laravel specific videos – even while never having run laravel once.
    4 points
  2. It's a module that adds extra color variation to Reno admin theme. Maybe someone will find it useful. Features (can be disabled or enabled): Sticky header with action button always visible notices at the bottom fixed sidebar Disabled accordion on Pages and Setup domain name with "open home page in new tab" Not tested with Admin on Steroids. Usable with disabled all option in this module and enabled sticky compact header in AdminOnSteroids. Not everything in every combination play well, but should be ease to set up these modules together. Before install change admin theme to Reno (works best with blue colors but is usable with Reno and classic) and this module will do the rest. The good idea is to change admin theme for guest as well to enjoy matching login screen. https://github.com/pmarki/Processwire-Admin-Dark-theme
    3 points
  3. Maybe obvious, but I just realized that a checkbox field without a headline does not show it's convenient field-edit popups.
    2 points
  4. $this->modules->get('JqueryUI')->use('modal'); After that you should be able to see the modal if your link has the "pw-modal" class. If you need to add buttons to the modal, follow the instructions in "\wire\modules\Jquery\JqueryUI\modal.js"
    2 points
  5. Best thing would be to strip it back to basics to try and narrow down the problem: Remove any textformatters applied to the field. Try removing all the content from the field. Try the simplest template file possible, that just echos the field with no prepended or appended files. Try adding the field to a new template that doesn't contain any other fields (besides title) and see if you still get the problem there.
    2 points
  6. Some good news! I have experimented with the background for transparent images. I have tried lots of checkerboard images, with two or three colors, with alpha transparency or not. Finally I came to the conclusion that it is much better to use some photoshop noise. Here is my testimage. A png with black, white and midgrey text / symbols plus a grayscale full opaque and half transparent: And here is a screenshot how it looks as thumbnail in the images field with some noise background: This way we would not need any steroids, no config settings, nothing else.
    2 points
  7. Thanks Ivan, I really appreciate it! You give me way too much credit and are too kind, but such a heartfelt message still leaves me speechless, so thank you again. I don't think I want any kind of luxury car! I'll be honest, while I was sad to give the car back, I was also glad to because it's just plain stressful. There's no problem if someone dents my car or something gets scratched, etc., but borrowing such a fancy car makes you always worried about where you park. If a bird poops on it you have to clean it right off, and so on and so forth. All these things I never worry about, but became apparent when I had to be responsible for such an object for 2 days. I imagine a lot of stress comes with owning something like that. I'm sure to many it's worth it, but still, glad I don't have to think about that kind of stuff every day. If I were to ever own a car like this, I'd buy it after it's already many years old, inexpensive, and has the battle scars to show it. \
    2 points
  8. hi everyone, i'm happy to share my first little module that could have broader use... use at your own risk! i'm quite new to module development Usage Just install the module and place your preview images in the folder /site/templates/TemplatePreviewImages filename = template-name.png Github https://github.com/BernhardBaumrock/TemplatePreviewImages Notes jquery image picker used in this module (MIT license): http://rvera.github.io/image-picker/ Room for improvement / roadmap: Images are resized via CSS (height: 200px) Images could be placed via masonry or the like create image-field to upload preview images directly to the template looking forward to hearing your feedback ps: is it intentional that i am only allowed to choose from 2 templates when adding the page and have more options available when editing the template settings of the page like you can see in the video? i'm wondering why this should be like this?!
    1 point
  9. No, sadly I don't own a Tesla Model S. Instead I own a 1994 Mazda. But with getting ProcessWire 3.x ready to release, I didn't have a lot to write about this week. So figured, why not chat about something else I'm passionate about (this is a blog after all). Last weekend, I got to pretend that I owned a brand new 2016 Tesla Model S (P90D) for two days and a couple hundred miles. I was so inspired by it, I figured why not write something. We'll even attempt to draw some parallels with ProcessWire. This post also covers updates to several 1st party modules. https://processwire.com/blog/posts/tesla-model-s/
    1 point
  10. In this tutorial I will cover how to use clsource's REST Helper classes to create a RESTful API endpoint within a PW-powered site and how to connect to it from the outside world with a REST client. This is a quite lengthy tutorial. If you follow all along and make it through to the end, you should get both, a working REST API with ProcessWire and hopefully some more basic understanding how these APIs work. As always with PW, there are many ways you could do this. My way of implementing it and the code examples are loosely based on a real world project that I am working on. Also, this is the first tutorial I am writing, so please bear with me if my instructions and examples are not that clear to understand. And please let me know if something is missing or could be made more clear. The steps covered: create templates and pages in the PW backend to get an API endpoint (an URL where the API can be accessed at) copy and save the REST Helper classes to your site create a template file and write some logic to receive and process data through our endpoint and send data back to the REST client test the whole setup with a Browser REST Client Addon I will not go into fundamentals and technical details on how RESTful APis are supposed to work. I assume that you have already read up on that and have a basic understanding of the principles behind that technology. Some helpful resources to brush up your knowledge: https://en.wikipedia.org/wiki/Representational_state_transfer http://www.restapitutorial.com/lessons/whatisrest.html The complete pages.php template is attached to this post for copy/paste. Lets get started. 1. create templates and pages in the PW backend to get an API endpoint (an URL where the API can be accessed) First we need to create some templates and pages in the PW backend to make our REST API accessible from the outside world through an URL (API endpoint). In my example this URL will be: https://mysite.dev/api/pages/ Note the "https" part. While this is not mandatory, I strongly recommend having your API endpoint use the https protocol, for security reasons. Further down in step 3 we will use this URL to create new pages / update and get data of existing pages. Go to your PW test site admin and: create 2 new templates: one is called "api", the other one "pages". For a start, they both have only a title field assigned. Just create the templates. We will create the corresponding files later, when we need them. enable "allow URL segments" for the "pages" template. We will need this later to access data sent by the requests from the client. in the Files tab of the "pages" template check "Disable automatic append of file: _main.php" create a new page under the home page with title, name and template "api" and set it to hidden create a child page for the "api" page with title, name and template "pages" The pagetree should look somewhat like this: Ok, now we're all set up for creating our API endpoint. If you browse to https://mysite.dev/api/pages/ you will most likely get a 404 error or will be redirected to your home page as we do not have a template file yet for the "pages" template. We will add that later in step 3. 2. copy and save the REST Helper classes to your site I have the REST Helper class sitting in site/templates/inc/Rest.php and include it from there. You could save it in any other location within your site/templates folder. I forked clsource's original code to add basic HTTP authentication support. Click here to open my raw gist, copy the contents and save them to /site/templates/inc/Rest.php In the next step we will include this file to make the classes "Rest" and "Request" available to our template file. 3. create a template file and write some logic to receive and process data through our endpoint and send data back to the client This will be the longest and most complex part of the tutorial. But I will try to present it in small, easy to follow chunks. Since we access our API at https://mysite.dev/api/pages/, we need to create a template file called "pages.php" for our "pages" template and save it to /site/templates/pages.php. Go ahead and create this file (if you're lazy, copy the attached file). Now right at the top of pages.php, we start with <?php require_once "./inc/Rest.php"; to include the REST Helper classes. Next, we initialize some variables that we will keep using later on // set vars with the default output $statuscode = 200; $response = []; $header = Rest\Header::mimeType('json'); 3.1 retrieve data with a GET request Now that we have the basics set up, we will next create the code for handling the easiest request type, a GET request. With the GET request we will ask the API to return data for an existing page. To let the API know which page it should return data for, we need to send the page id along with our request. I am attaching the page id as an url segment to the API endpoint. So the URL that the client will use to retrieve data for a page will look like: https://mysite.dev/api/pages/1234 where 1234 is the unique page id. Add following code to pages.php // if we have an urlsegment and it is a numeric string we get data from or update an existing page: handle GET and PUT requests if($input->urlSegment1 && is_numeric($input->urlSegment1)) { $pageId = $input->urlSegment1; // GET request: get data from existing page if(Rest\Request::is('get')) { // get the page for given Id $p = $pages->get($pageId); if($p->id) { $pdata = ["id" => $pageId]; // array for storing page data with added page id $p->of(false); // set output formatting to false before retrieving page data // loop through the page fields and add their names and values to $pdata array foreach($p->template->fieldgroup as $field) { if($field->type instanceof FieldtypeFieldsetOpen) continue; $value = $p->get($field->name); $pdata[$field->name] = $field->type->sleepValue($p, $field, $value); } $response = $pdata; } else { //page does not exist $response["error"] = "The page does not exist"; $statuscode = 404; // Not Found (see /site/templates/inc/Rest.php) } } } else { // no url segment: handle POST requests } // render the response and body http_response_code($statuscode); header($header); echo json_encode($response); Lets brake this down: First we check for a numeric url segment which is our $pageId. Then the Rest Request class comes into play and checks what type of request is coming in from the client. For the GET request, we want to return all data that is stored for a page plus the page id. This is all good old PW API code. I am using the $pdata array to store all page data. Then I am handing this array over to the $response variable. This will be used further down to render the JSON response body. If the page does not exist, I am setting an error message for the $response and a status code 404 so the client will know what went wrong. The else statement will later hold our POST request handling. The last 3 lines of code are setting the header and status code for the response and print out the response body that is sent back to the client. You can now browse to https://mysite.dev/api/pages/1 where you should see a JSON string with field names and values of your home page. If you enter a page id which does not exist you should see a JSON string with the error message. Lets move on to updating pages through a PUT request 3.2 update pages with a PUT request Since our API needs to know the id of the page we want to update, we again need to append an id to our endpoint url. In this example we will update the title and name of our homepage. So the request url will be: https://mysite.dev/api/pages/1. For the GET request above, anyone can connect to our API to retrieve page data. For the PUT request this is not a good idea. Thus we will add basic authentication so that only authorized clients can make updates. I use basic HTTP authentication with username and password. In combination with the https protocol this should be fairly safe. To set this up, we need an API key for the password and a username of our choosing. We add the API key in the PW backend: add a new text field "key" and assign it to the "api" template. edit the "api" page, enter your key and save. (I am using 123456 as key for this tutorial) Now add following code right after the if(Rest\Request::is('get')) {...} statement: // PUT request: update data of existing page if(Rest\Request::is('put')) { // get data that was sent from the client in the request body + username and pass for authentication $params = Rest\Request::params(); // verify that this is an authorized request (kept very basic) $apiKey = $pages->get("template=api")->key; $apiUser = "myapiuser"; if($params["uname"] != $apiUser || $params["upass"] != $apiKey) { // unauthorized request $response["error"] = "Authorization failed"; $statuscode = 401; // Unauthorized (see /site/templates/inc/Rest.php) } else { // authorized request // get the page for given Id $p = $pages->get($pageId); if($p->id) { $p->of(false); $p->title = $sanitizer->text($params["title"]); $p->name = $sanitizer->pageName($params["name"]); $p->save(); $response["success"] = "Page updated successfully"; } else { // page does not exist $response["error"] = "The page does not exist"; $statuscode = 404; // Not Found (see /site/templates/inc/Rest.php) } } } Breakdown: We check if the request from the client is a put request. All data that was sent by the client is available through the $params array. The $params array also includes $params["uname"] and $params["upass"] which hold our API user and key. We set API key and user and check if they match with the values that were sent by the client. If they don't match we store an error message to the response body and set the appropriate status code. If authentication went through ok, we get the page via PW API and update the values that were sent in the request body by the client. Then we put out a success message in the response body. If the page does not exist, we send the appropriate response message and status code, just like in the GET request example above. Now you might wonder how the client sends API user/key and new data for updating title and name. This is covered further down in step 4. If you want to test the PUT request right now, head down there and follow the instructions. If not, continue reading on how to setup a POST request for creating new pages. 3.2 create new pages with a POST request Final part of the coding part is creating new pages through our API. For this to work we need to implement a POST request that sends all the data that we need for page creation. We will do this at our endpoint: https://mysite.dev/api/pages/ Paste following code within the else statement that has the comment "// no url segment: handle POST requests": // POST request: create new page if(Rest\Request::is('post')) { // get data that was sent from the client in the request body + username and pass for authentication $params = Rest\Request::params(); // verify that this is an authorized request (kept very basic) $apiKey = $pages->get("template=api")->key; $apiUser = "myapiuser"; if($params["uname"] != $apiUser || $params["upass"] != $apiKey) { // unauthorized request $response["error"] = "Authorization failed"; $statuscode = 401; // Unauthorized (see /site/templates/inc/Rest.php) } else { // authorized request // create the new page $p = new Page(); $p->template = $sanitizer->text($params["template"]); $p->parent = $pages->get($sanitizer->text($params["parent"])); $p->name = $sanitizer->pageName($params["name"]); $p->title = $sanitizer->text($params["title"]); $p->save(); if($p->id) { $response["success"] = "Page created successfully"; $response["url"] = "https://mysite.dev/api/pages/{$p->id}"; } else { // page does not exist $response["error"] = "Something went wrong"; $statuscode = 404; // just as a dummy. Real error code depends on the type of error. } } } You already know what most of this code is doing (checking authorisation etc.). Here's what is new: We create a page through the PW API and assign it a template, a parent and basic content that was sent by the client. We check if the page has been saved and update our response body array with a success message and the URL that this page will be accessible at through the API for future requests. The client can store this URL for making GET or PUT requests to this page. If you're still reading, you have made it through the hard part of this tutorial. Congratulations. Having our code for reading, updating and creating pages, we now need a way to test the whole scenario. Read on to find out how this can be done. 4. test the whole setup with a Browser REST Client Addon The link in the heading will take you to a place from which you can install the very useful RESTClient addon to your favorite browser. I am using it with Firefox which is still the dev browser of my choice. Open a RESTClient session by clicking the little red square icon in the browsers addon bar. The UI is pretty straightforward and intuitive to use. 4.1 test the GET request Choose Method GET and fill in the URL to our endpoint. If you do not have a SSL setup for testing, just use http://yourrealtestdomain.dev/api/pages/1. If you happen to have a SSL test site with a self signed certificate, you need to point your browser to the URL https://yourrealtestdomain.dev/api/pages/ first in your test browser and add the security exception permanently. Otherwise RESTClient addon won't be able to retrieve data. If you have a test site with a 'real' SSL certificate, everything should be fine with using the https://... URL Hit send. In the Response Headers tab you should see a Status Code 200 and in the Response Body tabs a JSON string with data of your page. now change the 1 i the URL to some id that does not exist in your site and hit send again. You should get a 404 Status Code in the Response Headers tab and an error message "{"error":"The page does not exist"}" in the Response Body (Raw) tab. If you get these results, congrats! The GET request is working. For further testing you can save this request through the top menu Favorite Requests->Save Current Request. 4.1 test the PUT request Choose Method PUT and fill in the URL to our endpoint ending with 1 (http://yourrealtestdomain.dev/api/pages/1). In the top left click Headers->Content-Type: application/json to add the right content type to our request. If you miss this step, the request will not work. You will now see a "Headers" panel with all your headers for this request Click on Authentication->Basic Authentication. In the modal window that pops up, fill in user (myapiuser) and password (your API key). Check "Remember me" and hit Okay. You now should see Content-Type and Authorization headers in the "Headers" panel. Next, we need to send some data in the request body for updating our page title and name. Since we're using JSON, we need to create a JSON string that contains the data that we want to send. As I will update the home page for this example, my JSON reads { "title" : "Newhome", "name" : "newhome" } Be careful that you have a well formed string here. Otherwise you will get errors. Paste this into the "Body" panel of the REST Client addon. Hit send. In the Response Headers tab you should see a Status Code 200 and in the Response Body tabs a JSON string "{"success":"Page updated successfully"}". Now go to the PW backend and check if title and name of your page have been updated. If yes, congrats again. 4.2 test the POST request Choose Method POST and fill in the URL to our endpoint without any page id (http://yourrealtestdomain.dev/api/pages/). In the top left click Headers->Content-Type: application/json to add the right content type to our request. If you miss this step, the request will not work. You will now see a "Headers" panel with all your headers for this request Click on Authentication->Basic Authentication. In the modal window that pops up, fill in user (myapiuser) and password (your API key). Check "Remenber me" and hit Okay. You now should see Content-Type and Authorization headers in the "Headers" panel. Next, we need to send some data in the request body for updating our page title and name. Since we're using JSON, we need to create a JSON string that contains the data that we want to send. I will create a new page with template basic-page and parent /about/ for this example, my JSON reads { "template" : "basic-page", "parent" : "/about/", "title" : "New Page created through api", "name" : "newapipage" } Be careful that you have a well formed string here. Otherwise you will get errors. Paste this into the "Body" panel of the REST Client addon. Hit send. In the Response Headers tab you should see a Status Code 200 and in the Response Body tabs a JSON string "{"success":"Page created successfully","url":"https:\/\/mysite.dev\/api\/pages\/1019"}". Now go to the PW backend and check if title and name of your page have been updated. If yes, you're awesome! Summary By now you have learned how to build a simple REST API with ProcessWire for exchanging data with mobile devices or other websites. Notes I tested this on a fresh PW 2.7.2 stable install with the minimal site profile and can confirm the code is working. If you experience any difficulties in getting this to work for you, let me know and I will try to help. There purposely is quite a lot of repetion in the example code to make it easier to digest. In real life code you might not want to use procedural coding style but rather separate repeating logic out into classes/methods. Also, in life applications you should do more sanity checks for the authentication of clients with the API / for the data that is delivered by the client requests and more solid error handling. I skipped these to make the code shorter. RESTful services are by definition stateless (sessionless). My implementation within PW still opens a new session for each request and I haven't found a way around that yet. If anyone can help out this would be much appreciated. And finally big thanks to clsource for putting the Rest.php classes together. pages.php.zip
    1 point
  11. Hi! I've been making my first modules and I've created three so far to help me learn. I would love so feedback or pull requests for improvements as I hope to write a tutorial about my work soon. In particular the third modules isn't very finished. git: https://github.com/benbyford/PW-starter-modules/ HelloUserYouSaved - adds message {your user name, page saved} in admin when a page is saved. This module shows how to implement a basic module, get and use variables, create a message in the admin RedirectAdminPages - redirect specific user role to a custom page set in the module config. This module shows how to implement module configuration, using variables saved in the admin, redirecting a user using session->redirect() HotSwapUser - Swap user on the fly in the admin or frontend of your site This module shows how users can be used in a module how to set a user permission how to install / uninstall something within your module how to create a function that can be output in the frontend of your site.
    1 point
  12. @Jonathan Claeys Please provide an example of the code you are using to try and get your media image URL. I haven't used Media Manager, but looking at the documentation for outputting to the front-end there are a couple of things to be aware of: 1. A Media Manager field returns an array (specifically a 'MediaManagerArray') so you need to treat it as such in your template even if it contains only a single media item. The docs suggest looping over it, but if a MediaManagerArray is also a WireArray (the docs aren't specific about that) then you could use other API methods to get items such as first() or get($key). 2. The media itself (an image in your case) is contained in the media property of an individual MediaManager object. So you need to use methods like url or size() on the media property and not on the MediaManager object. Assuming that a MediaManagerArray is a WireArray and that your Media Manager field is called my_media_field: $media_manager_array = $page->my_media_field; $media_manager_object = $media_manager_array->first(); $image_object = $media_manager_object->media; $url = $image_object->url; echo "<img src='$url'>"; This is just to give you the idea, and is more verbose than necessary.
    1 point
  13. This is great, thanks. I see now we need to save complete config data not just one field. $this->modules->setModuleConfigData($name, $config); ^ This didn't work for me, but the following did: $this->modules->saveModuleConfigData($name, $config);
    1 point
  14. Hmmm. Hehe, sounds funny indeed! Seeing is believing, so let's give it a try
    1 point
  15. Hello for all, but first thanks to Bernhard for this module! I also created something for similar usage (layout switcher, first image), but also do some additions to this nice module (second image). Here in attachment is TemplatePreviewImages module version where I added some options: thumbnails creation (before usage need to create "thumbs" folder eg: "template/images/TemplatePreviewImages/thumbs) can use any kind of image extension (jpg, jpeg, gif, png) zoom option to preview (using PW integrated jQuery UI ) can restrict module to works only inside desired page tree Regards. TemplatePreviewImages.zip
    1 point
  16. It certainly can do that. But you could also go with PageTables, which can have different types of pages added to it. The most difficult question for you is probably, that you need to settle on some kind of structures blocks (one or more), which will later be pieced together to your tutorials. If you know how this might look like then this'll determine whats the best field to choose for the job.
    1 point
  17. Laravel is popular in the processwire community. But look also around where you live what software companies there are looking for php coders such as zend or symphony so you better learn a framework that you both can use in processwire and work with in a company nearby.
    1 point
  18. $this->className() in the ModuleConfig will return the name of the config class not the module (as would get_class()). Just remove the …Config suffix. But as soon as you're passing it the correct module name it's going to work wherever you need it. Also I'm not really sure if this kind of functionality actually should be put in the config module in the first place. It's convenient, but a actual function of the module, triggered on init() if a specific config is set, might actually be the better structure.
    1 point
  19. $name = $this->className(); // Namespace aware $config = $this->modules->getModuleConfigData($name); // Before 3.0.16 $config['my_checkbox'] = ''; $config = $this->modules->setModuleConfigData($name, $config); // Before 3.0.16
    1 point
  20. @tpr: finally found time to take a closer look at the language tabs issue. So far there appear to be two issues behind the scenes: VersionControl stores all language values in the form of "data[language-id]", but the field name for the default language is actually just "data". I'm pretty sure this used to work at one point, so perhaps it was a core change somewhere between 2.4 and 2.6 (have to setup a test site with earlier version to make sure). When built-in language tabs are enabled, CKEditor instances are not loaded before a specific tab is opened. This is a bit of a problem, since I can't set a value of a CKEditor instance unless it's already there. This requires a bit of testing, but I'll try to get these sorted out soon.
    1 point
  21. Glad you like it @bernhard. I'm very happy with it too. They offer a lot for free and their pricing is really reasonable when you grow.
    1 point
  22. I would consider this an issue. If I get you right, it only doesn't work with the new approach? I assume, it has to do with the automaticly parsed / rendered method of PW, that reads your code (as default setting) and then overrides it with the current modules settings. No chance to override a setting for us. Butthis is a valid use case. I think we should make an issue on github and see, if Ryan can add this more fine grained control back for us.
    1 point
  23. Thanks @Juergen, this should be fixed in v052. There's a new feature to FileFieldTweaks (named FileFieldToolbar before v052) that allows downloading assets - images or files. To keep things simple I've used the "download" HTML5 attribute which doesn't work in IE, at least in IE11. I don't plan to fix this because the download link will open in a new window if it's unsupported so it's still usable.
    1 point
  24. You probably want to change the value as well.
    1 point
  25. This module should work with images / pwImage plugin: http://modules.processwire.com/modules/form-helper/ You could test it or take a look in the source how it work.
    1 point
  26. Hi guys, Thanks for the replies. They all seem like viable options. Since starting this thread I've been reading more about PW and having a play with it, so I feel confident I could even create my own if none of the suggested solutions works for me. PW seems like a really cool solution for my project.
    1 point
  27. Q: What has the TESLA that PROCESSWIRE does not have: A: backdoors
    1 point
  28. Added IntercoolerJS response header methods... Maybe I reduce the number of methods (for example combine setPollingInterval, cancelPolling, resumePolling with a param to switch case). /** * Set x-ic-trigger response header * @param array $array One or more events with related data arrays */ public function trigger($array) { $json = json_encode($array); header('x-ic-trigger: ' . $json); } /** * Set x-ic-script response header * @param string $js Valid javaScript code */ public function script($js) { header('X-IC-Script: ' . $js); } /** * Stop current / parent element Intercooler polling */ public function cancelPolling() { header ('x-ic-cancelPolling: true'); } /** * Resume current / parent element Intercooler polling */ public function resumePolling() { header ('x-ic-resumePolling: true'); } /** * Set current / parent element Intercooler polling interval * @param string $interval */ public function setPollingInterval($interval) { header ('x-ic-setPollInterval: ' . $interval); } /** * Set x-ic-refresh response header * @param string $pathCsv Comma separated paths to refresh. */ public function refresh($pathCsv) { header('x-ic-refresh: ' . $pathCsv); } /** * Set x-ic-open response header * @param string $url New window / tab address */ public function open($url) { header('x-ic-open: ' . $url); } /** * Set x-ic-redirect response header * @param string $url Redirect destination address */ public function redirect($url) { header('x-ic-redirect: ' .$url); } /** * Add ajax redirect handler to Session::redirect */ public function hookSessionRedirect($event) { $this->redirect($event->arguments[0]); $event->replace = true; } Also successfully tested AjaxIntercoolerJS with Frontenduser I'll do some more tests with PW inputfields (via FormHelper) soon.
    1 point
  29. After trying several SaaS options I've settled with StatusCake (referral) for a year now. They offer free unlimited servers. You can receive an e-mail free (or use several third party integrations) or text (costs a little like 25$ for 100 credits). The only drawback is that you can't select from which location you want to check and you might find the 5 min interval too slow. But hey: it's free Right now I'm thinking of upgrading to get additional 1 minute checking, Locations, SSL Monitoring and Page Speed tests for 20$ a month.
    1 point
  30. I just integrated this module in a ProcessWire 3.0.30 project and it works.
    1 point
  31. I managed to get the Embed plugin working by following the steps you outlined (adding all dependency plugins, manually adding toolbar button), and then also: Uncheck "Convert div tags to paragraph tags" Set "Use ACF?" to "No". I suppose you could keep ACF active but then you would have to add all the elements/attributes/classes that could potentially be inserted by the plugin into the "Extra Allowed Content" field. Looking at the Embed plugin source it only adds div[!data-oembed-url] as allowed content, but when you check the markup that is added for a YouTube embed (for example) you see a lot of other markup besides the div. There also something going on regarding allowed content in the Widget plugin but I found it difficult to decipher.
    1 point
  32. @bernhard thanks, I've fixed the submenu gap in the main nav. I also managed to fix the "hoverSaveDropdown" issue (flicker on hover). It's only CSS and I have to test a little more but it's promising. The solution is to hide the "dropdown" part of the button and add the down arrow with :after. Plus I had to add pointer-events: none to the span inside the buttons as they also caused flickering. I underestimated this issue because it wasn't as noticable in the Reno theme as in the default. Now it seems fine in both of them. As for the centered logo in the login page: I'm not sure about it. I like that it sits in the corner but if there are others who vote for it, then let it be.
    1 point
  33. I know someone has to write this, so let it be me. The first time I realised what I could do with the ProcessWire API it was like an insane mode in mentioned Tesla Model S. But it was just the beginning as PW keeps accelerating me ever since. Of course there are rough edges, but I am sure there are some in Tesla too - you just have to own it a bit longer to discover them . This creation of yours, Ryan, is something that was a mind-changer and a life-changer for so many of us here and more around the globe. And it is not just cheaper and better, it is open source and the best you can get! Tesla team made a great job. So did you - alone. More people everywhere in the world are using PW now than probably ever will be using Tesla cars. So the impact not only on the future, but on the present is quite comparable (Tesla team just has to work harder to not fall behind too far). ProcessWire is equally fine crafted mixture of technology and design, as this electric car... But none of us have to give it back some day soon. But not only the technology is to be mentioned. ProcessWire is a community, open source and global. People from Africa use it alongside people from Europe and Americas. And they (actually we) come together every day to talk to each other about a topic of no envy and hatred, but a common love and perspective. The world seems to be so unstable and fragmented these days. At the place that I live I hear a lot of negative words aimed at US and its policy. Some of it might be true, some of it is an obvious propaganda. But without other channels of information and communication you can easily lose your own point of view. I am sure something similar is happening on the so called "other side". Here in community we overcome that way of thinking. You, Ryan, and the open source ProcessWire thing is doing better job for creating a world as a better place than NSA spying scandals and troops being brought to places abroad for sure. And your avatar is the most friendly face of America to be seen for many. I do not know if making one of the best pieces of software in the world for free and inspiring one of the most friendly and helpful international communities shall ever help you to buy a luxury electric car (I really hope so), but "at least" your children have something to be really proud about.
    1 point
  34. Thanks. Currently working on some pending fixes, but I'll take a closer look at these soon
    1 point
  35. I might found a bug: On a multilanguage CKEditor field, if I try to restore a revision, always the last language tabs' value is restored (not sure if this is true, I have only 2 languages). Furthermore, the loading span doesn't go away, I had to set display: none to see the results. Or does it remain there to avoid manual editing? If not, I would use display: not or perhaps pointer-events: none to enable clicking. Now I can't even switch language tabs. Maybe only setting a lower opacity (with pointer-events: disabled) and using :after pseudo to add the loader animation would do. This could be achieved simply by toggling a class on the element. I can help you with this if you need.
    1 point
  36. This is my most ambitious PW site yet: http://vroom.pt It's an auto ad portal specially designed towards professional dealers. Some highlights you can't really see just browsing the website: Custom CMS for dealers (screenshot); Auto generated, customizable website for each dealer (examples here and here); The dealer can choose between a dark or light theme, then set a tone color; More themes will be added in the future with completely different designs. Optimized search algorithm to keep speed reasonable even when searching through thousands of results.
    1 point
  37. hi, i also think that this would be a great addition but should NOT be the only option. playing around with the jquery demo (http://jonom.github.io/jquery-focuspoint/demos/helper/index.html) i see that it would lead to problems when you only want to show a small part of the image that is located near the border of the image. i think a more advanced concept like the imagefoucsarea plugin would be better. the best would be to have the good old cropping plugin with predefined ratios and/or dimensions, have a simple focus point option and even more have a more advanced focus-area option like in the plugin linked above
    1 point
  38. Yep. You just aim between the eyes and that's it
    1 point
  39. This demonstrates the idea: http://jonom.github.io/jquery-focuspoint/demos/helper/index.html
    1 point
  40. I'm currently missing a quite useful feature in the module. I've the following setup to prevent unnecessary verbosity, where client accounts are defined like so: role=client, company=SomeCompany (page field). This way I just need to define each company in a single place as well as handle the client role permissions and access rules once. Now I've a list of projects, where clients should only be able to see those projects, where the company field does hold their assigned company. This is certainly possible with dynamic roles right now, but it's introducing the verbosity that I tried to avoid, meaning I need to have at least a single drole per client. I'd much rather use a single drole to handle all clients and assign them view access like so: template=project, client=user.client. From looking into the code I think this would mostly be another "where" check for mysql queries and the runtime permission checks should be even more simple to implement. @renobird I'm not sure if you still need it, but dynamic roles do not work on admin pages (process modules). See this for a working solution: https://processwire.com/talk/topic/6822-module-dynamic-roles-for-pw-246/page-3#entry98415
    1 point
  41. Here is something I hacked together quickly for automatically adding new child pages to the pagetable field. This is only if you are using the page as the parent. It also handles deletion of items if they are trashed externally. I also disabled the internal check for orphans - because they have been automatically added already, there is no need for the "Children were found that may be added to this table. Check the box next to any you would like to add." option. I seems to be working great here, but please test carefully!! Add this to your admin.php file: wire()->addHookBefore('InputfieldPageTable::render', function($event) { $pp = wire('pages')->get(wire('input')->get->id); $ptf = $event->object; //remove pages from pagetable field if they were externally trashed foreach($pp->{$ptf->name} as $item) { if($item->is(Page::statusTrash)) $pp->{$ptf->name}->remove($item); } //add pages to pagetable field if they were created externally foreach($pp->children as $child) { if(!$ptf->has($child->id)) { $pp->{$ptf->name}->add($child); $pp->of(false); $pp->save($ptf->name); } } //reset orphans property so that we don't get a message asking to add new pages that are now already automatically added $ptf->setOrphans(new pageArray()); });
    1 point
  42. roles.on speed u sholud.call it adderole
    1 point
  43. This is already implemented in the upcoming version 2.3. Try it yourself by downloading the Dev branch on GitHub.
    1 point
  44. For sites without a lot of fields, I think that adding a groups designation would just be confusing, at least for new users. So would ideally like to find something that you don't really notice until you are specifically looking for it. How about if the field's 'advanced' tab had a text input where you could enter one or more tags? When used, the fields list would include a list of tags in use at the top, and clicking any one of them would make the list show only fields with the clicked tag.
    1 point
×
×
  • Create New...