Jump to content


  • Posts

  • Joined

  • Last visited

Contact Methods

  • Website URL

Profile Information

  • Gender
    Not Telling
  • Location
    St. Louis, USA

Recent Profile Visitors

1,870 profile views

jordanlev's Achievements

Full Member

Full Member (4/6)




Community Answers

  1. @pideluxe - I think we are in agreement. I am not judging the entire PW system on the ability to create custom application functionality... all I did was explain where the limitations are when trying to do so (again, because the OP asked me to, not because I'm actively trying to give PW a bad name or anything). @Beluga - I unfortunately cannot do this because the data contains customer names and contact info. And I unfortunately don't have enough spare time to go through and anonymize the data or recreate it with dummy data (sorry, I agree it would be a good case study though).
  2. @LostKobrakai - I wouldn't consider "more than one person working on a site" an advanced use case. In my experience, most CMS's suffer from this problem, so it's not something that is unique to ProcessWire -- but it seems to me that for some situations, storing the *definition* of the field structures in a config or code file, while keeping the data in the database is ideal. I utilize this system with a plugin I offer for the Concrete5 CMS where designers can set up their own content field definitions via a point-and-click dashboard interface, but the results of their pointing-and-clicking is saved to a php array. The data itself is *not* normalized into separate database fields though... so there is definitely a tradeoff (the plugin I make is best suited for page content that is not queried in any context other than "give me all the content on this one page that is being viewed"), and I don't think the way ProcessWire is structured would allow for such a setup. But other CMS's do utilize this approach -- Bolt CMS and October CMS come to mind, as well as the flat-file CMS's such as Statamic and Kirby. So I'm not suggesting that ProcessWire should (or can) be changed, but it is a limitation of building an application in PW. And another reason that if you're building a "custom application" as part of the larger website, you might want to consider using plain old SQL files or a db migration library and do it the old fashioned way instead of leveraging ProcessWire's "everything can be a page" approach.
  3. @kongondo - I think we are saying the exact same thing, but perhaps my words have more of a negative spin than yours do. I agree with @Sephiroth that there seems to be a "mantra" on the forums that "everything is a page" and that the built-in tools can handle anything and everything... I think this can hurt newbies like myself who go down the wrong path. I just wanted to have a contrary opinion out there so people can see the "boundaries" or limits of the system and make informed decisions about their projects. (Also the OP specifically asked me for my thoughts via a private message @Sephiroth - I would be delighted to have a more detailed discussion about these things... I am *very* opinionated about how I think CMS's should work What is the best way to engage in a conversation about this? (I'm not sure I'd be able to just write it all up, but if it was more of a back-and-forth conversation or answering specific questions I can certainly do that). The last thing I will say is that all of you people here on the forums are wonderful and if ProcessWire continues to grow and become successful, it will be as much because of the helpful and friendly community as it is because of the technical underpinnings. So keep up the great discussions! Thanks, Jordan
  4. @matjazp , for my custom application that I recently made in ProcessWire, I assumed that leveraging the built-in ProcessWire tools would save me a lot of time because I would not have to code up my own "CRUD" forms (dashboard forms for the site owners to add, edit, and delete records). I created "templates" and "fields" instead of creating my own database tables and fields. Many people had suggested that utilizing the PageTable field type would give me a ton of flexibility in how I structure my data relationships and turning those into editable interfaces without requiring any programming on my part. However, I ran into a few problems. The first big problem is that I did *NOT* want this portion of the application to be managed via the "pages" sitemap tree in the dashboard. I know that it can be very flexible and would save me a lot of development time, but it does not provide the streamlined and intuitive interface for my clients that I like to deliver to them... it just doesn't make sense to them why they would be editing their products in the same exact kinds of forms as their content pages. In addition to the sitemap tree not making sense for this use case, there are just too many tabs of fields all over the place, and it was difficult to understand how (or if it was even possible) to customize this editing interface for my clients. So, what I wound up doing is creating my own dashboard pages so I could customize the forms exactly the way I wanted. This was okay once I figured out how to "carve out my own niche" in the dashboard, but it took a lot of work. It was difficult to leverage the built-in "input" modules so that I could avoid building my own form logic (see this post for some details on how to make it even possible, because out-of-the-box it doesn't work without some modifications: https://processwire.com/talk/topic/8061-problems-with-image-uploads-when-including-processeditpage-form-on-another-admin-page/ ). The 2nd problem I ran into is that all of the template and field definitions are stored in the database, as opposed to config files or code itself. I understand the benefits of this in terms of making certain kinds of applications very easy for non-programmers to build because they can "point and click" their way to defining a data structure. But for my team this was a big challenge because it means we can't keep the actual data schema and template/field settings in version control. We had to pass around a database from designer to developers, and back and forth from staging servers and development machines and the live server. The 3rd problem I ran into is when it came time to do aggregate reporting. As I alluded to in that other thread you linked to, the ProcessWire system is basically a "database within a database", where each field is its own table. I had a fairly complex schema (although not totally crazy in my opinion) where I had customers, delivery locations, delivery schedules, orders, line items, and products all combined into one list (basically "show me all of the products in all of the orders that are to be delivered to customers on day x at location y"). This site has tens of thousands of orders per month, so the query was dog-slow (like, taking 1-3 minutes to run). What I had to do was spend a LOT of time "untangling" the ProcessWire query logic and write my own SQL query with a lot of JOINs in it... after I made this custom SQL query it ran in under 1 second! So, at the end of this project what I realized is that as a programmer who already has a lot of experience building my own forms and my own "CRUD" interfaces and my own database schemas and SQL queries, as well as my business being based on delivering very customized user interfaces to my clients... ProcessWire had nothing to offer me on the "custom dashboard application" side of things. All it did was put some new layers of abstractions that I had to learn and then work around in my way, when what I really wanted was to build things the tried and true way that has worked well for me for over a decade (HTML forms, PHP form processing via a "controller" of some kind, and a database schema with SQL queries for complex reporting). All that being said, I did not use the "Form Builder" that others are talking about, but I'm not sure that would offer the functionality you're needing in a dashboard interface (maybe it does, I don't know -- haven't used it). Also I understand that my requirements may be a bit more advanced than others... if someone did need to build out a custom application and was okay leveraging the built-in tools and compromising on a rather clunky editing interface, then ProcessWire would be an amazing tool to use. And of course I'm only talking about custom applications here... in terms of the templating and the front-end portion of the site, working with PW is a dream come true... I gladly await the day when every CMS and platform out there has the API consistency and "stay out of my markup"-ness as ProcessWire
  5. @triples, I run a lot of C5 sites, and have no problems with speed on version 5.6.x. I believe that version 5.5.x had some issues with caching, but they seem to have been resolved with the 5.6. release. I haven't yet tried the newest version (5.7) because it has some usability issues that need to be worked out, and I've also heard reports that the speed isn't there yet. So, I'd say the 5.6 version of C5 is just as fast as any CMS I've used. Of course, any system can be made to run faster or slower depending on how you use it. For example, I built an eCommerce site with ProcessWire a few months ago, and I went along with the common advice here that everything should be treated as a "page"... each customer is a "page", each order is a "page", each product is a "page", each invoice line item is a "page" (none of these pages are displayed on the front-end, but in terms of data architecture that is how I have it set up). This turned out to be a very bad decision because of the fact that every field is actually its own table in the database, it makes reporting abysmal. I had to deconstruct the PW query builder and come up with my own SQL query to get any kind of reasonable performance on the "order reports" page... and it is like 20 JOINs in one query. The code is now not very easy to understand which is going to make maintenance more challenging then if I had built out a normal schema with normal database tables/records (instead of trying to shoehorn my data model into PW's "everything is fields+templates+pages" system). I don't mean to bash ProcessWire... but my point is that any system can be made to run faster or slower depending on if you're using it for the things it was designed for or not (and if you do things efficiently or not). Comparing one system's demo site to another system's real-world buildout is not a fair comparison. All in all, I'd say that ProcessWire's strong points are definitely its consistent and well-thought-out API, and its incredibly clean templating. But the editing interface is very clunky (although I know this is a matter of subjective opinion) and if you don't want "everything to be a page" then all the built-in field functionality isn't very easy to use in other contexts. Best, Jordan
  6. Mystery solved: I actually *did* have an image field associated with every template because I had a "meta image" field (for facebook/pinterest shares etc) as a GLOBAL field... so I need to un-global that field and manually go through and assign it to only the pertinent templates. Hopefully then all the empty folders won't be created.
  7. I've had a site up and running for a few months now, and I just peeked inside the /site/assets/files directory and there are over 27,000 directories in there! Most of them are empty, and my guess is that Processwire is creating a new directory for every "page" in the site. (99% of these "pages" are not for front-end, but rather are data records representing customers/orders/line-items/etc -- but none of these have image or file fields associated with them). I found this forum post from 2012: https://processwire.com/talk/topic/1585-module-clean-empty-directories-from-siteassetsfiles/ ... where Ryan says that the core was updated (a couple of years ago now) to not create folders for every page, but it seems that it's not happening for me. I'm running version 2.5.3, so it's relatively recent. How do I keep this from happening? Is there a setting somewhere I missed? Or do I need to schedule a cron job to clean out empty folders periodically or something? Thanks, Jordan
  8. I have a template for 'order', and another for 'order-item'... each order is like an invoice and each order-item is like a line item on the invoice (for a specific product). What I'd like to do is retrieve all orders that contain a certain product, and I'm not sure how to achieve this in an efficient manner. The naive approach would be to do something like this: $find_this_product = $pages->get('template=product, name=the-product-I-want'); $order_items = $pages->find("template=order-item, order_item_product=$find_this_product"); $orders = array(); foreach ($order_items as $order_item) { $orders[] = $order_item->belongs_to_order; } Problem with that (I'm guessing) is it's going to make a separate database query for each order_item. To reduce the number of queries, I'm thinking I could instead loop through the "order_items" and combine their order id's into a pipe-delimited string, then use that string of ids as a selector (e.g. $pages->find(id=1|2|3|4|5))... but that seems kind of yucky to me (especially since there might be hundreds or thousands of orders for a particular product). Ideally what I'd like to do is recreate this kind of SQL logic in my selector: SELECT DISTINCT orders.* FROM orders INNER JOIN order_items ON orders.id = order_items.order_id WHERE order_items.product_id = X; Is this possible to do in an elegant fashion with the processwire query engine? Or do I need to resort to SQL to grab all the ids and combine them into a string? Thanks. EDIT: I realize my title is a bit confusing. When I say "children", I mean "conceptual children"... the orders and order_items (and products) are related to each other by a Page field... I am not necessarily connecting them by parent/child location in the sitemap.
  9. Below is some full working code for a process module that manages pages of a specific template. To install it, create a new folder in your site's "site/modules" directory called "ProcessCustomPageAdmin", then inside that new directory create a file called "ProcessCustomPageAdmin.module" and paste the code below into that file. Then install from your site's admin back-end (you'll need to "refresh" the directory to get PW to recognize it, just like with all new modules you try to install manually). A few things to note: The "create" and "delete" actions respond to GET requests, which is possibly dangerous. The "create" action is probably ok because this is behind your admin backend so you don't have to worry about webcrawlers accidentally hitting the pages. But depending on how important the data in the pages is, you might want to make it respond to a POST request only and put up some kind of confirmation. I was trying to keep things as simple and focused on your question as possible so I didn't include any of that stuff. There is no functionality to sort the pages. You need to output your own markup for the list view if you want to achieve this and then wire up your own "sort" action and set up JQueryUI sortable on the list display... way outside the scope of this forum topic here. You'll want to output this snippet of CSS on that page to hide the id that gets outputted for the CKEditor to function. Create a "ProcessCustomPageAdmin.css" file in your module directory and PW will automatically load it for you.​#Inputfield_PageIDIndicator { display: none; } Last but not least, you need to change the $template_name and $parent_page_selector variables in the module class to suit your needs. Best of luck! <?php class ProcessCustomPageAdmin extends Process { public static function getModuleInfo() { return array( 'title' => 'Custom Page Admin', 'summary' => 'Dashboard interface for managing pages', 'version' => '100', 'author' => 'Your Name Here', 'permission' => 'page-edit', 'page' => array( 'name' => 'custom-page-admin', 'title' => 'Custom Page Admin', ), ); } private $template_name = 'your-template-name'; private $parent_page_selector = 'template=parent-page-template'; //determines where new pages are added under (can be any page selector) public function execute() { $table = $this->modules->get('MarkupAdminDataTable'); $table->setEncodeEntities(false); $table->setSortable(false); $pages = $this->pages->find("template={$this->template_name}, sort=sort"); foreach ($pages as $page) { $table->row(array( htmlspecialchars($page->title), "[<a href=\"{$this->page->url}/edit?id={$page->id}\">Edit</a>]", "[<a href=\"{$this->page->url}/delete?id={$page->id}\">Delete</a>]", )); } $table->action(array('Create New Page' => "{$this->page->url}/create")); return $table->render(); } public function executeCreate() { $page = new Page(); $page->template = $this->template_name; $page->parent = $this->pages->get($this->parent_page_selector); $page->title = 'Untitled Page'; //note that we don't need to set a name because it is autogenerated (as per the parent template settings) $page->save(); $this->session->redirect($this->page->url . '/edit?id=' . $page->id); } public function executeEdit() { if ($this->config->ajax) { return $this->modules->get('ProcessPageEdit')->execute(); //ajax-y form widgets (e.g. image uploader) need to be handled by the real ProcessPageEdit module (but for some reason they look to the form action for their ajax url instead of always going to /[admin]/page/edit) } $page = $this->getPageById($this->input->get->id); $action = "{$this->page->url}/edit?id={$page->id}"; $form = $this->buildPageEditForm($action, $page); if ($this->processPageEditForm($form, $page)) { $this->setPageNameFromTitle($page); $this->session->message('Page saved.'); $this->session->redirect($this->page->url); } Wire::setFuel('processHeadline', $page->title); return $form->render(); } public function executeDelete() { $page = $this->getPageById($this->input->get->id); $page->delete(); $this->session->message('Page deleted'); $this->session->redirect($this->page->url); } /*** HELPER FUNCTIONS ***/ private function getPageById($id) { $id = (int)$id; if (empty($id)) { throw new Wire404Exception('Missing or invalid page id'); } $page = $this->pages->get($id); if (!$page || ($page->template != $this->template_name)) { throw new Wire404Exception('Unknown page (it may have been recently deleted or had its template changed)'); } return $page; } //pass in empty string for cancel_button_url to not include one private function buildPageEditForm($form_action, $page, $include_save_button = true, $cancel_button_url = '') { //code inspired by: https://gist.github.com/somatonic/5011926 $modules = wire('modules'); $form = $modules->get("InputfieldForm"); $form->method = 'post'; $form->action = $form_action; foreach($page->getInputfields() as $input_field) { $form->add($input_field); } if ($include_save_button) { $form->add($modules->get("InputfieldSubmit") ->set('name', 'submit') ->set('value', 'Save') ); } if (!empty($cancel_button_url)) { $form->add($modules->get("InputfieldButton") ->set('name', 'cancel') ->set('value', 'Cancel') ->set('href', $cancel_button_url) ->set('icon', 'times-circle') ->set('class', 'ui-button ui-widget ui-corner-all ui-priority-secondary') //gives it a faded look ); } //IMAGE UPLOADER WIDGET NEEDS THIS TO FUNCTION PROPERLY (note that the "name" is only so we can hide this via CSS... but the only thing the image uploader needs is the p tag): $form->add($modules->get("InputfieldMarkup")->set('name', 'PageIDIndicator')->set('value', "<p id='PageIDIndicator'>{$page->id}</p>")); //CKEDITOR IMAGE BUTTON NEEDS THIS TO FUNCTION PROPERLY: $form->add($modules->get("InputfieldHidden")->set('name', 'id')->set('value', $page->id)); return $form; } private function processPageEditForm(&$form, $page) { //code inspired by: https://gist.github.com/somatonic/5011926 $input = wire('input'); if (!$input->post->submit) { return false; } $form->processInput($input->post); if ($form->getErrors()) { //pass true to clear the errors return false; } $page->setOutputFormatting(false); foreach($form as $field) { $page->set($field->name, $field->value); } $page->save(); return true; } private function setPageNameFromTitle($page, $append_number = null) { $name = wire('sanitizer')->pageName($page->title); if (!is_null($append_number)) { $name .= '-' . (int)$append_number; //yes, we want to explicitly cast to int and then implicitly cast back to string (via concatenation) } if ($name == $page->name) { return; //avoid the page finding itself as a dup in the query below } else if (wire('pages')->count("parent=$page->parent, name=$name")) { $append_number = (int)$append_number + 1; $this->setPageNameFromTitle($page, $append_number); } else { $page->set('name', $name)->save(); } } }
  10. Well, after a ton of debugging and stepping through code, I've begun to understand what the problems I was having are. Unfortunately these require very specific fixes to the way that specific inputfields work (there's not some global setting), so I would imagine that there are other field types I haven't gotten to yet that will cause problems as well. But for what it's worth, here is how to fix the issue with the image uploader widget and the CKEditor image button: IMAGE FIELD (2 things required): * The image uploader needs to make an ajax request to the ProcessPageEdit page (/processwire/page/edit), but instead of using the actual url to that page it retrieves the form action. Since I've changed the form action to post back to my own page, this was resulting in the ajax call not getting what I needed. To fix this, I added this at the very beginning of my "executeEditMyPage()" function: if ($this->config->ajax) { return $this->modules->get('ProcessPageEdit')->execute(); } * The image uploader needs to know what page it is working with, so add this somewhere on the page (it can live anywhere on the page, but I'm adding it as an "InputfieldMarkup" field to the form so everything is self-contained there): $form->add($modules->get("InputfieldMarkup")->set('name', 'PageIDIndicator')->set('value', "<p id='PageIDIndicator'>{$page->id}</p>")); (note that the image uploader only needs that p tag, but I am also setting a "name" on the inputfield so that the generated markup gets an id I can then hide via css, like so: #Inputfield_PageIDIndicator { display: none; })CKEDITOR IMAGE BUTTON (1 thing required): * The ckeditor image plugin needs to know what page it is working with, but it looks for a different element than the image uploader widget does. So add this to the form as well (this actually needs to be a form field): $form->add($modules->get("InputfieldHidden")->set('name', 'id')->set('value', $page->id)); VOILA!Wish me luck when it comes time to figure out Repeater and PageTable
  11. I just thought of a more succinct way to ask my question (for those who don't want to read through my long rambles): Does anyone ever use the built-in "image" inputfield on pages other than ProcessPageEdit? What about the CKEditor? If so, how exactly do they make those work outside the confines of the specific markup on the ProcessPageEdit admin page? Do I need to surround them with specific elements/classes/id's? Or do I need to make sure certain JS files are included (other than the ones that the inputfield module outputs itself automatically)? Surely I'm not the first person who wants to allow image uploads outside the context of a normal page edit operation?
  12. Thanks for the response. I will give your suggestion to extend ProcessPageEdit a shot, although I will try to explain exactly what I'm wanting to do here. The situation is that I have a somewhat complex data model. Products are being sold on specific dates in specific locations, and at each location there are different product variations (or "product options"... like different sizes, each with different prices). Kind of like a company that goes around to farmers markets or fairs and sells things, but depending on the season and what they have in stock, they might have certain products available one week but not the next, and also they might need to charge different prices at different weeks depending on how hard it was to get something. (Also also, they might have different product variations/options available from week to week, because they might run out of one option or size but then get more in stock a few weeks later, etc.). It seems that the general consensus amongst the PW developer here is that I can use the built-in page tree as my editing interface for this data. It's true that I can do that, but it does not meet my standards for providing a "guided interface" to my clients who need to manage this data. Here are some examples of the things that I don't like about using the built-in pages interface for managing this data: There will be generic content pages on this site ("home", "about us", "terms & conditions", etc.), AND there will be pages that are populated by the product/location/dates-of-sale/variations/etc data. To the client, these are different things because the generic content pages are more free-form and might look very different from week to week, but the "data" stuff is much more structured and ties into their actual business (not just the marketing of the business). So I think it would be confusing to have to use the same "page tree" interface to manage both the pages of the site and the "data" of the site. Instead I'd prefer to have a separate section in the admin interface that is specific to the management of the "data", and then they just use the page tree for the generic content pages. This I am able to achieve very nicely via a ProcessModule (as I explained in my other recent thread here: https://processwire.com/talk/topic/8043-how-to-provide-admin-interface-for-editors/?p=77757 ). Using the built-in "page edit" admin pages burdens the client with too many options. The only tab I want them to see is "content", not "settings" or "delete". I don't want users to have to see the "page name" field, because these are pages that don't correspond to pages on the site front-end... so why should the user have to care about the url slug? I think there are ways around this one though with various settings. I can use the PageTable field to manage the "sub-records" (for example, the product variations that are applicable to a certain week-of-sale), but it does not give me the ability to enforce certain constraints. For example, in a particular week they will add the various locations that they are travelling to. The list of possible destinations exists as another template... so there is a "page" field that allows them to choose which location they are adding a sub-record for. But each time they add another sub-record (via the PageTable field), it shows them the entire list of cities again. This means they could possibly add 2 sub-records of the same city, which will cause problems. It just doesn't make sense in the data model that the same location would have 2 sub-records in a particular week. Another problem with the PageTable interface is it opens the sub-page in a modal dialog and it too has the tabs at the top. I *only* want the "content" tab to appear. And I can actually make this happen by going into the database for the template and adding "noSettings: 1" to the json data for the fields. But it still shows the "content" tab, even though it's the only tab. It takes up a lot of vertical real estate and is one of those things that isn't a huge deal but it's still less than perfect. In general, I think the "edit"/"move"/"view" buttons in the page tree are not very nice. Please don't hate me I totally understand that this is a matter of opinion, and most people seem to like them, so that's fine. But I think it would be better to have actual buttons next to each item in the list. So really what it comes down to is I want to leverage the individual "field" interfaces (inputfields), but not be forced to use them in the built-in ProcessPageEdit page or the Page Tree. I was hoping that because ProcessWire is so modular and well-thought-out, that this would not be a difficult thing to achieve. But perhaps this is not the case, which would be a bummer. Because then it seems my options are to give up and deliver a not-very-polished editing interface to my client, or re-build all of PW's functionality so I have the control to make things just the way I want (and at that point, I might as well not even use a CMS and just build a from-scratch app... which I *really* was hoping to avoid). Thanks for your time and assistance, it is greatly appreciated. I know I'm being very particular here, but the complete markup flexibility is what attracted me to PW in the first place, so I hope it's something the community can appreciate
  13. Hi, I'm using this snippet from soma: https://gist.github.com/somatonic/5011926 to render and process a page's edit form on my own admin page (via a process module). It all seems to work very well, except there are some problems with some of the more advanced input types, like the image field's drag-and-drop file upload does not work, and using the PageTable field kinda-sorta works mostly but has problems rendering the table sometimes or it adds a new page but doesn't "connect" it to the parent properly. My guess is that these issues are related to missing javascript, but the css and js files for all of the inputfields are being outputted to the page. I've also made a call to wire('modules')->get('ProcessPageEdit') just to give that module a chance to output its own css/js as well (and when I look at the page source I see that its css/js files are in fact there in the header). Note that I am in the admin section here... this is not for "Front-end editing" or anything like that. Or perhaps there are some element classes or ids in the "ProcessPageEdit" display itself that the javascript expects to find? But how could this be the case since other people make admin themes so they can't assume that the overall page markup is going to be the same? Anyone have any ideas on how to get this to work? Thanks! EDIT: Also the "image" button on the CKEditor toolbar doesn't work (it pops up a dialog with a PHP error in it about 'pages' being null)
  14. Well, it appears that the module *is* working... it's just that the button doesn't show up on pages of the "admin" or "home" template. Thanks for the tip @adrian... that is a cool feature (although not very intuitive... I didn't notice it until you specifically mentioned it... but maybe that's the point
  15. Hey @soma, I see what you mean about having the pages outside of the "Admin" section... I wasn't sure I would be able to hide them effectively until Craig mentioned this in his response above. As for re-creating the editing interface... my issue is that I actually have a more complex data model than what I've used for an example in this thread. Specifically, a product can have "product variations" and "product locations". The product variations each have a name and a price (and some other miscellaneous info). The product locations also have additional info (so it's not just a reference to a location page from a product page). What I'm imaging is having sub-pages under each product for "variations" and "locations", then a page type for "product-variation" and another page type for "product-location". I'm concerned that it will get too tricky for my users to have to remember to add these various things in the right place. Instead I'd like for them just to be able to view a list of products, then click on a product to see a list of BOTH the variations AND the locations, and edit all that info in one place. (I know what you're thinking: I can have a "page" field that allows multiple selections... but again the problem is they aren't just choosing variations and locations, rather there is associated information pertaining to each one). So maybe there is a way to achieve this management of complexity via the built-in page tree? Maybe some kind of Table or PageTable field? I would be very open to hearing suggestions... which is why I posted this question in the first place (and am really glad to have gotten so much good info from you and the other guys). Last: Can you please explain in detail how to achieve "you can render part of the tree in your module and have them edit using pw edit screen and sort or delete them with a few lines of code"... I would *love* to see this code, if you could provide it. Thank you!
  • Create New...