-
Posts
5,963 -
Joined
-
Last visited
-
Days Won
288
Everything posted by bernhard
-
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
What do you mean, I don't understand? -
I think this is perfectly fine, but why not add this as a method in your class to get rid of the hook? // in your pageclass public function tools() { // get tools based on page name $toolsClass = ... // return instance of tools return new $toolsClass(); } // usage $pages->get(...)->tools()->foo(); The benefit is that your IDE will understand your code and if you add return types etc. it will help you with code completion.
-
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
Thx for sharing! Yeah that's basically the way I have been building things as well for a long time. But adding all the fields and getting every single detail done correctly is so much work, so I decided to finally do it better in a reusable way that has a good and compact ui for clients and does not rely on a multitude of fields. What do you mean by hiding past occurrences? In my case I'm creating events via rrule.js and the start date is always the first event page's date. So recurring events will always be in the future (relative to the first event). This is the UI for creating events and that table shows the items to be created once the user clicks on "create events". That view is really nice as it updates instantly, so anyone should get a very quick understanding of what all the settings do: The idea is to get all the necessary tools for handling events with as minimum effort as possible. So I've already built the RockDaterangePicker field last month. The next step was to add a calendar view. I first added that to the frontend, but then I realised how much effort it is to setup all necessary ajax endpoints and handling all clicks and all that, so I decided to move that into the backend. If anybody needs to show these events on the frontend, this will be as easy as a foreach + page selector or just adding a simple fullcalendar, which is also easy as long as you don't have to deal with managing events (edit, move, change etc). And then I realised that when having all that ready in the backend it might be the right moment to also tackle recurring events. So at the moment the concept is that you add a calendar field to one parent page. There you define which pages to show as events (which will likely be the children of the parent page, but could be any other selector or hook as well). Then for the events all you have to do is to add the daterange field which will be created during installation of the module. This field will tell the calendar where to show events (on which day and time) and it will also save all the info whether the event is part of a series etc... -
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
Great to hear that! I'm also very motivated as this has been an issue for me (and I guess many of us) for a long time. Things are really going well so far. I had some troubles today with timezone issues (events starting at 10:00 suddenly started at 11:00 from one month to another etc.) and also with the performance of creating recurring events. Turned out I set a generic pagename and PW had to append a unique suffix for every created page and that got slower and slower as pages under that parent grew in count. I've just quick-fixed that by setting a random name via uniqid() and the performance is quite impressive imho (real world speed on my macbook air with ddev): How cool is the live progress bar??? π It works with realtime feedback from the server using SSE. No polling. No sending hundreds of requests to the server π I also wanted to update the grid above the progress bar, but that also turned out to slow things down a lot, so I turned that off for now. I have to look into that tomorrow. I think it should be an easy fix. But that's it for today π -
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
Absolutely true, thx! I think you are right and I'll not add this. Instead I'll try to make the editing interface via FullCalendar as smooth as possible. I think that's the best common ground that every installation will have. Once they have added their holidays to ther calendar they will see them in the month view and then they can move/clone events to the desired dates by drag&drop. That's already possible by just clicking on the trash icon before creating recurring events π Yep, and I've made good progress so far π What you mention will be supported. That's how it will work (or as mentioned one can exclude items before creation) π -
PagePaths is part of the core, just not installed. In your ProcessWire backend go to Modules > Core and install "Page Paths" module from the list. @Robin S I guess your module could install Page Paths automatically, no?
-
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
Thanks! Yeah I've been there several times but never really managed to get something solid. Great!! I'll send you a copy as soon as I have something usable. Wow, that will be very helpful for my project! Thank you. The company behind is even Austrian π I can think of adding "holiday" as an option to the rrule interface. There one could select "Austria" and then I could add a callback that loops over all rrule dates (eg "every day until 1.1.2025") and filters out non-holiday days, which would result in only holiday dates in the events grid of to-be-created events. -
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
That's a very slick interface, congrats @Stefanowitsch Unfortunately to support all possible options there are some more options and this is what I came up with so far: This seems to work for almost all use cases that I could think of so far. The interface could even be improved by hiding options that don't make sense (but it's not so easy to define which they are and when). The only case I don't have a solution so far is "every sunday or holiday at 20:00" Anybody knows or has a good idea how to support holidays as recurrence rule? That's obviously a challenge, because holidays are very specific by region... My best idea so far is to add a "clone" feature to the month calendar view where the client could just drag and drop the event (a guided tour through a cave) from sunday to a holiday and click "clone" instead of "move". That way they could quickly add all events for all sundays and then drag them over to all the holidays... -
RockPageBuilder v5.6.0 We now have customizable block stubs! ππ₯ @FireWire requested that feature in the forum and I thought it was a great idea, so I added support for it. You can now define your very own boilerplate code with custom classes that you need for your specific project. See the docs here. Added the "rocksortable-added" event so that you can attach custom callbacks to the sortable instance. I'm using this to apply some project-specific classes after block order has been changed (to update the text color based on the current background color of multi-colored pages): See the docs here. I shared a little screencast here and think that is a really cool way of adding color sections to any site. Added the field() method to $block objects. Make sure to also update RockFrontend to the latest version! Fixed wrong sorting of blocks with Umlauts.
-
RockMigrations v5.2.0 Added a snippet for the RockIcons module/fields. Added a deprecation note for Magic Field Methods. This feature has been moved to RockFrontend, because the way I implemented it to RockMigrations was not ideal. It added a hook for every existing field, which was something I wanted to change for a long time. But as I didn't see any noticable performance penalties it didn't happen until recently π If you have been using magic field methods be sure to update RockFrontend to the latest version and refactor your code until you don't get any deprecation notices in your logs! Logs will be shown in the "magic-pages" log and will even have a notice how to fix it:
-
RockFrontend v3.20.0 User Contributions β€οΈ @gebeer provided a Pull Request to improve Livereload on slow internet connections and @stefanowitsch fixed an issue with the rf-scrollclass feature. Thank you! Livereload now shows how often it refreshed the browser for you in the console. On my current project it shows "Loading LiveReload - 3721" which means RockFrontend saved me from hitting the refresh button for 3721 times already. If you haven't tried LiveReload be sure to check it out! There is a new field() method. Check out the docs here.
-
What do you think of something like this? // somewhere let HelloWorld = ProcessWire.hookable( { foo: "foo world!", ___hello: () => { return "hello world!"; }, }, "HelloWorld" ); console.log(HelloWorld.hello()); // output: hello universe! console.log(HelloWorld.foo); // output: foo universe! // somewhere else ProcessWire.addHookAfter("HelloWorld::hello", (e) => { e.return = "hello universe"; }); ProcessWire.addHookAfter("HelloWorld::foo", (e) => { e.return = "foo universe!"; }); I built a proof of concept module here, but it's already outdated and I'll work on a new version shortly. The reason why I'm building this is because I needed a way to modify some parts of my JS frontend setup on my RockCommerce project. So I added two methods RockCommerce.after(...) and RockCommerce.before(...) where we as a developer and user of RockCommerce customise every part of the Frontend (for example adding custom taxes or pricing calculations). Now while working on RockCalendar I wanted something similar. And while working on RockGrid I had the same need. For example adding custom locales or adding custom callbacks. What is easy as cake in PHP is not so easy to do in JS. So I thought, wouldn't it be nice to have hooks in JS as well? I asked Ryan and he seems to like the idea, so I'll work on that over the next few weeks. As you can see here I will most likely change the module soon to work with JS proxy objects. This is what provides the magic of AlpineJS behind the scenes. Now I'm wondering if some basic Alpine magic would make sense here as well, for example watching a property and firing a callback can be extremely helpful on its own! let demo = ProcessWire.magic({ foo: "foo", init() { this.$watch("foo", (newVal, oldVal) => { console.log(`foo property changed from ${oldVal} to ${newVal}`); }); }, }); demo.foo = "bar"; // will log "foo property changed from foo to bar" I've renamed ProcessWire.hookable() to .magic() in this example, as it does more than just adding hook support. Not sure about "magic", maybe you have better ideas? What do you think? Would that be helpful? What would be a good name? ProcessWire.rock(...) would be my favourite I guess π ProcessWire.proxy(...) would also be an option. Not sure if adding basic apline magic to PW would be a good idea of if adding alpinejs itself would be better? Any JS experts here that want to help with that project?
-
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
That's an interesting use case @Ellyot_Chase Would that be just a single checkbox or a daterange or an hourly schedule? Don't see a problem here as my calendar will be able to list any page as long as it contains a RockDaterangePicker field (which stores all the information about start timestamp, end timestamp, allDay yes/no etc. That would be regular PW pages and page reference fields. I'll keep your use case in mind! Thx -
Single page select value type: which do you prefer?
bernhard replied to Jonathan Lahijani's topic in General Support
I'd love to have something like this, where we can write code that doesn't break if something or someone changes an output formatting setting of a field and where we can request the value we need wherever we want: // force single value $p = $page->getPageOrFalse('my_page_ref_field'); if($p) ... // force page object $p = $page->getPageOrNullpage('my_page_ref_field'); if($p->id) ... // force array value $items = $page->getPageArray('my_page_ref_field'); foreach($items as $item) { ... } If you like that, give it a thumbs up: https://github.com/processwire/processwire-requests/issues/538 -
Hi @notplants welcome to the forum and thx for your contribution! There is no standard way of adding requirements. ProcessWire does not use composer or such. It is just a platform to run modules. How you add your dependencies basically is up to you. One option is to include it into your module. So you'd do composer require ... on your dev environment and then you add require vendor autoload to your module and that's it. That means it is super easy to install for anybody else, but that also means that if you (or anybody else) had multiple modules that require guzzle in the best case it would just be some overhead (as every module might ship a separate version of guzzle) and in the worst case you'd get conflicts. Another option would be to create another module solely for adding guzzle to PW. That way several other modules could use the guzzle module and you'd have less overhead, but more to do during installation or maybe also more troubles as you need to keep versions compatible... The third and in this case IMHO best option is to use WireHttp instead of guzzle unless you really need guzzle for the http requests?! WireHttp is part of the core so you get the best of option 1 and option 2.
-
Today while working on RockCalendar I had the need to change the database schema of my daterange fieldtime to add support for recurring events. I didn't know how to do it, so I had to do some research and that took quite some time. Here's the solution that I found in FieldtypeComments.module. When developing the fieldtype you can add a database schema like this and PW will take care of creating the table and columns for you: public function getDatabaseSchema(Field $field) { $schema = parent::getDatabaseSchema($field); $schema['data'] = 'timestamp NOT NULL'; // the from timestamp $schema['foo'] = 'timestamp NOT NULL'; return $schema; } This is quite easy, but I wanted to add another column and tried this: public function getDatabaseSchema(Field $field) { $schema = parent::getDatabaseSchema($field); $schema['data'] = 'timestamp NOT NULL'; // the from timestamp $schema['foo'] = 'timestamp NOT NULL'; $schema['bar'] = 'timestamp NOT NULL'; return $schema; } No luck. You will get an error that column "bar" does not exist. Ok, so we have to modify the table somehow... But we also have to make sure that this is only done once. How to we do that? The solution is to save the schema version to the field and use that to compare versions and conditionally update the schema: public function getDatabaseSchema(Field $field) { $schema = parent::getDatabaseSchema($field); $schema['data'] = 'timestamp NOT NULL'; // the from timestamp $schema['foo'] = 'timestamp NOT NULL'; $schema['bar'] = 'timestamp NOT NULL'; $schemaVersion = (int) $field->get('schemaVersion'); $updateSchema = true; $table = $field->getTable(); $database = wire()->database; if ($schemaVersion < 1 && $updateSchema) { try { if (!$database->columnExists($table, 'bar')) { $database->query("ALTER TABLE `$table` ADD bar " . $schema['bar']); } $field->set('schemaVersion', 1); $field->save(); } catch (\Throwable $th) { $this->error($th->getMessage()); $updateSchema = false; } } return $schema; } And maybe at a later point you want to add another column "baz": public function getDatabaseSchema(Field $field) { $schema = parent::getDatabaseSchema($field); $schema['data'] = 'timestamp NOT NULL'; // the from timestamp $schema['foo'] = 'timestamp NOT NULL'; $schema['bar'] = 'timestamp NOT NULL'; $schema['baz'] = 'timestamp NOT NULL'; $schemaVersion = (int) $field->get('schemaVersion'); $updateSchema = true; $table = $field->getTable(); $database = wire()->database; if ($schemaVersion < 1 && $updateSchema) { try { if (!$database->columnExists($table, 'bar')) { $database->query("ALTER TABLE `$table` ADD bar " . $schema['bar']); } $field->set('schemaVersion', 1); $field->save(); } catch (\Throwable $th) { $this->error($th->getMessage()); $updateSchema = false; } } if ($schemaVersion < 2 && $updateSchema) { try { if (!$database->columnExists($table, 'baz')) { $database->query("ALTER TABLE `$table` ADD baz " . $schema['baz']); } $field->set('schemaVersion', 2); $field->save(); } catch (\Throwable $th) { $this->error($th->getMessage()); $updateSchema = false; } } return $schema; } π
- 1 reply
-
- 7
-
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
I think this should be doable with a custom sort callback in fullcalendar in v6: https://fullcalendar.io/docs/eventOrder -
Request for Input: What features should a PW calendar module have?
bernhard replied to bernhard's topic in Modules/Plugins
Thx @BrendonKoz and @Jonathan Lahijani that's very valuable input. I have read your article briefly and it's an interesting idea to build the frontend calendar on your own. On my quick and dirty tests i added the fullcalendar to the frontend to see if everything works. Then I added the mentioned drag and drop functionality to see if editing events also works. It did. But it needed quite a lot of not so easy code and to get something modular I had to refactor everything. Now I built the fullcalendar as a fieldtype for the backend, so anybody can easily add a calendar to the PW backend. This already works very well for managing events, resizing them, moving them, etc.; But the display part is currently also handled by FullCalendar which works, but also has downsides. For example the mobile view of the month is not ideal. I have to experiment more with it to finally decide, but there is room for improvement at the current state. On the other hand the folks at FullCalendar have built a very good product and for example styling the calendar is a breeze with just setting css variables to your needs. @Jonathan Lahijani how do you deal with multi-day events and how to you decide how they stack and what do you do if you have more events than what fits in one cell? -
For a current project I have the need to show and manage events. First, I thought I'd just show events as a list. The benefits of this approach are that it is very easy to do and it works well on desktop and mobile. Then I had a chat with @gebeer and we concluded that a real calendar interface is far more intuitive for the average user. I've built such a calendar once on an ancient site (https://www.mistelbach-mustangs.at/events/), but it was a lot of work and so I didn't do it again for any other project. Then I thought let's use google calendars for managing events. That would have the benefit that we get a lot for free (the whole gui for managing events, the data storage, recurring events, etc). But it also comes with downsides: First, clients need to create an account for their calendar on a third party. We will hopefully have many clients on that project, so instructing them to create an account somewhere else and then connecting both apps together is a lot of overhead. Second, events handled by google have a totally different data structure than PW pages. What if I wanted to display those events? What if I wanted to add image galleries to those events? What if I wanted to have event descriptions powered by RockPageBuilder? What if I wanted the best performance one can get using the awesome ProCache? These things are very easy to do when we are dealing with PW pages, but they are hard if we talk to a third party api like the one from google. So I decided to build RockCalendar. A module where a FullCalendar shows PW pages and all the tedious things are already built in (like managing events, creating events, resizing events, managing locales, etc). I've made good progress over the last few days and I think I'll have something to share next month, so I thought I'd ask for feedback what the community thinks would make sense for such a module? Have you ever had the need for such a module? If yes, what would be the key features that you'd want to see in such a module? What would be nice to have? What would be questions that come up in your head? I can't promise, but I'll try my best to incorporate the community's feedback and suggestions into the RockCalendar module to make it as useful and versatile as possible.
-
I'm working on RockCalendar which will be released soon if everything goes smoothly π I think it should be stable enough next month. If you want to get notified you can subscribe to the Rock Monthly Newsletter. The module uses https://fullcalendar.io/ for the calendar interface and when clicking an event it will open the page editor in a pw modal: Opening the modal was a bit of a challenge, because PW unfortunately does not offer a good JS API to open modals. It only offers markup-based options to control the behaviour of the modal - at least as far as I could find out. This is a problem, because all events in the calendar get loaded by fullcalendar and I only have the eventClick() callback where I need to fire my action. My solution is to create a fake element in the dom and trigger a click on that element: calendar.on("eventClick", (info) => { // create a fake link element in body let link = document.createElement("a"); let $link = $(link); $link.attr( "href", ProcessWire.config.urls.admin + "page/edit/?id=" + info.event.id ); $link.addClass("pw-modal"); $link.attr("data-autoclose", ""); $link.attr("data-buttons", "button.ui-button[type=submit]"); $link.on("click", pwModalOpenEvent); $(document).on("pw-modal-closed", this.refresh.bind(this)); $link.click(); $link.remove(); }); Maybe that helps anyone else looking for a solution to a similar problem. If anybody knows a better way how to do it, please let me know! PS: If you have input (feature requests) for the development of RockCalendar please let me know: https://processwire.com/talk/topic/30355-request-for-input-what-features-should-a-pw-calendar-module-have/
-
I've done a video about DDEV, but it doesn't go through setting up ddev. Just follow the instructions on the ddev website. For this you need to tell tracy debugger where the files live on your local file system. This is because PW + Tracy run inside the container and inside the container your files live in /var/www/html. So if you click on a debugging link in tracy then your OS tries to find the file /var/www/html/foo.php and obviously can't find it. // tracy config for ddev development $config->tracy = [ 'outputMode' => 'development', 'guestForceDevelopmentLocal' => true, 'forceIsLocal' => true, 'localRootPath' => '/path/to/your/project/', 'numLogEntries' => 100, // for RockMigrations 'editor' => 'cursor://file/%file:%line', ]; The important part for you is the "localRootPath" setting.
-
Looking for an AI assistant for code? Consider Supermaven
bernhard replied to gornycreative's topic in Dev Talk
Jep, since 12.1.2024 π https://processwire.com/talk/topic/29439-cursor-might-be-my-vscode-replacement/#comment-238405 For me it's absolutely worth the 20β¬ per month. It helps me a lot with JS and CSS and sometimes also PHP, but the better you are with a language the less often you'll need help from the AI. I think so, yes. -
RockFrontend Site Profile - RockFrontend + UIkit + TailwindCSS ??
bernhard replied to bernhard's topic in Themes and Profiles
What exactly? Maybe it also loads other .less files (in addDefaultFolders()) that reference a variable from uikit. What you are trying to do should definitely be possible so I'm sure we'll get it to work π -
As you don't provide any details we can only guess. Maybe you want to use markup regions but they are disabled in config.php?
- 4 replies
-
- rockfrontend
- tracy debugger
-
(and 1 more)
Tagged with:
-
Hi @Atlasfreeman I'm sorry but I don't understand what you are trying to say. What is file.php? What is index_filter.php? These things might be obvious for you but they are not for me/us. Every PW project is different, so you have to explain your setup in more detail. I don't understand what you mean by "catches all the page references". The RockPageBuilder field is a PW field like any other field. You output it like any other field in PW, see https://www.baumrock.com/en/processwire/modules/rockpagebuilder/docs/blocks/#rendering-blocks If you don't want to output any blocks on any page, don't add the field to the template and don't add the render call in the template file. ---- Maybe anybody else understands your questions better.