-
Posts
16,772 -
Joined
-
Last visited
-
Days Won
1,530
Everything posted by ryan
-
You actually can use the 'sort' property, but you'll want to perform the sort after you've assigned it to all your items, because PW will write them out in the order that they appear. For instance, here is how we might reverse the order: $cnt = count($page->images); foreach($page->images as $image) { $image->sort = $cnt; $cnt--; } // now tell it to sort by the field 'sort' $page->images->sort('sort'); // you may not need to do this, but putting it here just in case $page->trackChange('images'); $page->save(); Avoid calling $page->images->remove() just because that will queue an actual file to be removed when the page is saved. Another way you might accomplish reversing the order: $myImages = new Pageimages($page); foreach($page->images as $image) { $myImages->prepend($image); } $page->images = $myImages; $page->save();
-
Thanks, I didn't realize that was out of date. I have updated it to mention the $config->maxUrlSegments setting.
-
You are close on this. You can't actually give a field a different name. A field name is the same no matter what template you put it on. It is a constant. Though you can change the label or description according to the context of a template. Fields are not fieldtypes, they are variables on a page. There are fieldtypes in ProcessWire, and you can have as many of the same fieldtype on a template/page as you want. You do have to create the fields (of your chosen types), and assign them to your template. But just like you can't have two variables in PHP named $foo in the same namespace, you can't have two fields on the same page named 'foo'. If you need another field just like 'foo', then clone it and name it 'bar' or 'foo2' or whatever you want. You can create as many copies as you need. In the admin, Setup > Fields serves as your master directory of all fields in your site. To take the example further, some types in PHP can contain multiple values, i.e. arrays. The same goes for ProcessWire, as some fieldtypes are multi-value fieldtypes. Examples include page references, files, images, comments. There's also the 'repeater' fieldtype, which appears to throw all rules out the window, but that's in appearance only as it is technically mapping everything within the rules behind the scenes. Underneath it all, every field maps to a database table, ensuring that everything remains quickly selectable, searchable and consistent throughout the API.
-
I think we may be able to make this behavior configurable like we did with isset. I don't necessarily think it's a great thing to do, because it could add some really difficult to debug situations in site development. There's a reason why PHP throws an error when you call a non-existant method, and ProcessWire is trying to be consistent with that behavior of PHP. But just disabling the exception when Twig is active might not be a problem. I know you'd mentioned you found a workaround, but let me know if you still find this to be worthwhile.
-
The max items is a planned future addition. I'd originally planned on having it in the first version, but decided to keep things as simple as possible for the first go around. Max items will make an appearance in the next version. When you leave out a label for a field, it's going to show the name that it's using internally. The same goes for repeaters. But because repeaters need to have the same field repeated over multiple times, they get the ID appended to the field name. That's necessary because an HTML form is all operating in the same namespace, so we can't just refer to "this_field" as "this_field". Instead we have to refer to it as "this_field for repeater item ID 1234", i.e. "this_field_repeater1234". That's what you are seeing in the screenshot.
-
If a page just has a 'title' field and nothing else, then it doesn't go into an intermediate unpublished state. The reason for this has to do with the reason why other pages start in an unpublished state… Other pages start 'unpublished' because the editor wasn't able to see all the fields at the time they created the page. Obviously it would be premature for that page to enter a published state before the editor had an opportunity to populate it's fields. Whereas, when the editor creates a page that has nothing other than a 'title' field, they've seen all the fields there are at the time they created the page. The need for a page to go into an intermediate 'unpublished' state is much less likely. Granted, there are still the rare situations where you may actually want that page to be unpublished, even if you have nothing more than a 'title' (like if you are building the first page in a structure of pages). In such cases, after I create the page I click to the 'settings' tab and check the box for 'unpublished', then save. However, the vast majority of the time that users create title-only pages, the intermediate unpublished step is an annoyance. So the behavior is aimed at reducing annoyance. We didn't used to have this behavior, and there was indeed much annoyance with numerous accidental unpublished pages and the like.
-
Nesting Fieldset and FieldsetTab doesn’t work
ryan replied to Michael van Laar's topic in General Support
Double check with the default admin theme, just in case it's something with the admin theme you are using. However, I think that it is a bug because I seem to remember running into something similar months ago with nested fieldsets. Though I'd forgotten about it till now. I will take a closer look.- 5 replies
-
- fields
- FieldsetOpen
-
(and 1 more)
Tagged with:
-
I think it's a good idea in general, but Diogo is right that ProcessWire is a different type of CMS than the environment where you'd use something like that. The components of a page are defined by template rather than by page so that it is a consistent and reusable pattern that scales. Whereas a visual page builder is nice when you are working on small scale sites where the page is the template. I'd also echo the markup considerations Diogo mentioned. Both types of CMSs have their place, but the approaches are naturally different down to the core where the patterns of one don't necessarily make sense in the other.
-
What WillyC said (assuming I understood what he said)
-
I wasn't exactly sure how to do this, and if it'll work given that we're using a combo date+time picker, but I need to look into this further as soon as there is time.
-
This is correct. The admin UI doesn't let you select multiple fields to sort by yet. But your API calls can sort by as many fields a you want. It will use them in the order you specify them in the selector.
-
Are you sure you've got the latest commit? The Page::$issetHas = true; is what is designed to fix this exact issue. Make sure that you are setting Page::$issetHas = true; (exactly like that) before you initialize Twig. But I'm assuming you've done all this. As a result, the only reason I can think of why you'd get this error is if the page that was checked didn't actually have a 'summary' field in it's template. The error you are getting is from ProcessWire and it's throwing the error because Twig is trying to call a function called $page->summary(); and that function does not exist. So on the surface, it would look to me like Twig tries to call a $page->summary(); function if it finds that $page->summary; is blank. It seems like an unusual behavior... Twig doesn't accept something being blank and instead starts making arbitrary function calls using the property name. Maybe there is a way to turn off that behavior in Twig's config?
-
More updates to the blog profile at http://processwire.com/blogtest/ Still not done with it, but lots of new tweaks. The biggest one is the addition of Tags, as well as an update to the InputfieldPageAutocomplete (committed today) that makes it work really well for tagging. Now when you are entering something in the autocomplete, if it doesn't match anything you can just hit enter and it adds it as a new page. This is assuming that you've configured the field to support that feature. Anyway, the point of this is that it's a very natural way of adding new pages with autocomplete.
-
It's not possible at present to give other roles access to the trash. That is an area where access inheritance doesn't exist (since it's an anything-goes bucket 'o trash). It becomes a can of worms when considered in light of access control. Do you really want someone digging in your trash? A couple of alternatives: 1. Consider that /trash/ is just a page with children (albeit a smelly one). But you can just as easily make your own trash page. Rather than deleting pages, ask them to change the parent to your trash page (or drag their page into it). So long as they have access, they should be able to drag stuff in and out of it. If they pages they are dragging into it use templates that inherit access, and you make your trash page not viewable to guest, then any pages dragged into it are essentially removed from the site. 2. It sounds like you might be using trash as an unpublished area. If that's the case, I recommend just using PW's Unpublished status rather than the trash. 3. If you still want to use PW's system trash, you can create a template or module that lets them undelete stuff they've deleted. This isn't complete, but gives the basic idea: $deletedPages = $pages->get('/trash/')->find("modified_users_id=$user, include=all"); if(count($input->post->restore)) { $parent = $pages->get('/some/parent/'); foreach($deletedPages as $p) { if(in_array($p->id, $input->post->restore)) { $p->parent = $parent; $p->save(); echo "<li>Restored: {$p->url}</li>"; } } } // display list of their deleted pages and give them a 'restore' checkbox foreach($deletedPages as $p) { echo "<li><label><input type='checkbox' name='restore[]' value='{$p->id}' /> {$p->title}</label></li>"; }
-
Your example looks okay to me, and it should work. Try these to see if any fix the problem: 1. Try dragging your /blog/ to be a child of some other page, and then drag it back out to root. That should force a rebuild of the pages_parents index, used by the particular find() function you are calling. If there was a problem in the index, this would resolve it. 2. Try adding "include=all" to your selector, just in case the pages that aren't showing up are unpublished or hidden. Though for your production version, you probably don't want "include=all", but it's a good test for now. 3. Rather than $pages->get("/blog/")->find(...), try it without the get("/blog/'). That part is adding a little overhead, so if you aren't going to find pages using template blog-post outside of /blog/, then there's no reason to have that /blog/ filter there. So try changing it to this: $pages->find("template=blog-post, sort=-publish_date, limit=10"); 4. Are you certain that template blog-post has a field called publish_date and that it is a date field (not a text field)? And do all the pages in question have this field populated? Let me know if none of these fix it, or if #3 fixes it. If #3 works while the alternative doesn't, then I'd want to do a little testing here to make sure it's not a bug in PW's Page::find() function.
-
We also have an API function for this: $total = $pages->count("selector"); It basically works the same as @apeisa's example and is fast/low overhead.
-
Porl, yesterday I put in a commit that enables you to modify the behavior of the Page::__isset() function. For the PageTwig module, you are going to want to put this in your __construct() or init() method: Page::$issetHas = true; More info in the commit notes: https://github.com/ryancramerdesign/ProcessWire/commit/40ccfe2a05772f51a97c8a58e2c8721dfc0b51dd Thanks, Ryan
-
Allow setting ImageSizer upscaling via Pageimage->size()
ryan replied to teppo's topic in Wishlist & Roadmap
I think this is correct, that it really just depends the way you are used to working with images. For the sites I build, if I ask for an image of a specific size, it's because that's the size I need. I don't care what it has to do to get there, because the needs of my layout are more important than the image itself. An image of any size other than what I asked for would be inconsistent at best or a layout breaker at worst. I'm usually dealing with lots of images that I depend on being consistent with each other in size. I hate upscaling, but I hate inconsistency even more. If something has to be upscaled then I'm going to notice that and try to find a better image, but at least the damage is limited to the image rather than the layout or consistency. Here's another way to accomplish it. Put this somewhere in one of your first template includes: function sizeDown(HookEvent $event) { $width = (int) $event->arguments[0]; $height = (int) $event->arguments[1]; $image = $event->object; if($image->width < $width) $width = $image->width; if($image->height < $height) $height = $image->height; $event->return = $image->size($width, $height); } $wire->addHook('Pageimage::sizeDown', null, 'sizeDown'); Now you can substitute any $image->size() call with $image->sizeDown(): $image = $page->image->sizeDown(300, 200); -
Proper image type checking (instead of extensions) for ImageSizer
ryan replied to teppo's topic in Wishlist & Roadmap
This makes sense, thanks for the great explanation. I will pull this in to the ImageSizer class to have it check both extension and type. -
I was questioning this too, but couldn't decide what the headline should be? "Main" or "Top" or "Navigate!", it all just seems a little cheezy and unnecessary. But it would look good to have something there, just not sure what.
-
Is it only the repeater fields that don't save, or all the fields? I'm assuming all fields, but let me know if I'm wrong. Because you are doing this outside of ProcessPageEdit, you need to connect the values from your inputfields to the values in your page. Something like this: function formToPage(InputfieldWrapper $form, Page $page) { foreach($form as $inputfield) { $name = $inputfield->attr('name'); if($name && $inputfield->isChanged()) { $page->set($name, $inputfield->attr('value')); } if($inputfield instanceof InputfieldWrapper && count($inputfield->getChildren())) { formToPage($inputfield, $page); // go recursive } } } formToPage($form, $page); $page->save();
-
That's why it's going to come with defaults already populated and identified. So to be more clear, there will be a title, CSS selector and color picker. The title says what it's for (i.e. "Vertical borders") and the CSS selector targets them. The only thing the typical user will change is the color picker value. If someone wants to take it further and add their own extra repeater items to customize further, that's up to them. But I don't see or expect the non-developers to do that. Also, I fully expect people to make a horrible explosion of colors. Put even a single color picker into the hands of a non-designer and the results won't be pretty. But I'm not responsible for other people's color choices. Honestly, if there aren't a few explosions, then we're not making things configurable enough.
-
Allow setting ImageSizer upscaling via Pageimage->size()
ryan replied to teppo's topic in Wishlist & Roadmap
Nobody likes upscaling. But if I call a function asking for it to create something at a certain size, it's because that's the size required. If there are other conditions surrounding that, shouldn't it be left to the caller to decide? i.e. if($image->width > 300) $image = $image->width(300); If not wild about extra arguments (especially booleans) in API functions because they aren't self explanatory in the resulting code. So I'll only use them when absolutely necessary. Whereas, a bit of code like above is self explanatory to us now, and years from now when things like "what does the 3rd argument mean" are no longer fresh on our minds. On the other hand, I've got no problem with self explanatory function names, like widthNoUpscale(), but sometimes adding more makes the API less simple. -
You can edit the profile page directly and change the template that it uses. But it would need to be one that's doing the same thing as PW's admin template. A much simpler thing you could do would be to edit the existing /site/templates/admin.php and set it to add some stylesheet or JS to change the look. For instance: /site/templates/admin.php <?php if($page->name == 'profile') $config->styles->add($config->urls->templates . 'styles/profile.css'); require($config->paths->adminTemplates . 'controller.php'); You'd want to have a role called 'employee' that has page-view and profile-edit permissions, and nothing more. They will be able to edit their profile.
- 16 replies
-
- password protected
- admin
-
(and 1 more)
Tagged with:
-
Proper image type checking (instead of extensions) for ImageSizer
ryan replied to teppo's topic in Wishlist & Roadmap
Thanks for posting this! The SVN diff looks exactly like the Git ones. This seems like a good method, perhaps even in addition to extension filtering. But one thing I'm wondering is, does it change anything about the result? ImageSizer fails at it's own check rather than at GD's check, but seems like it would still fail. I'm just wondering how this solved the issue of BMP images renamed to JPGs?