 I'm a developer relation to Wrangla, I work at Automatic. This is 2023 and it's 10 years now since I've been working with WordPress. I'm also a former WordCamp Europe organiser. I was on the organising team for WordCamp Europe in 2018 in Belgrade, 2019 in Berlin and 2020 in Porto that got cancelled for, if we all know what, why. Right, so before we kick off, why would you want to migrate a short code to a block? Well, one reason is to improve the WYSIWYG experience for content editors and other non-technical users because there's a short code block. So if you've got a plug-in that implements a short code, you could put the short code in the short code block, but it just looks like, you know, it doesn't look great. It doesn't actually render the content in the editor and so users don't get that WYSIWYG experience, which is the intention of the block editor. Another good reason to convert your short code plug-in to a block is that you can add some features and functionality that either not, that can't be done, or it's not easy to do with a short code plug-in. And we'll go on to look at some, at how we can make the plug-in version or the block version of our plug-in had to have better functionality than the plug-in, the PHP short code version. You know, and as we go through this project, what we'll do is we can still retain the short code functionality for the backwards compatibility. So people who have used the short code block, the plug-in will still work, you know, whether the user uses the short code or whether they use the newly implemented block version. Okay, has everybody, there's a few things that were on the list that you needed to have. Has everyone got NVM, sorry, Node and NVM installed? Has everyone got Git installed? And has everyone got a WordPress environment like Lareval Valley or DevKinster or local? Yes, or MAMP? Anyone not got those? Okay, as we work through this thing, if you get stuck at any point, a couple of people are helping out in the room. There's Ryan here who will go around to just stick your hand up if you need help. And Christof at the back has also agreed to help out. So stick your hand up and one of them will come over. If they're both busy and I'm not busy talking, I can come out and help you as well. Okay, so I have to keep moving the cursor over here in order to move to the next slide. Right. Okay, first of all, I need you to... In your WordPress installation, go to the WP Content Plugins directory and then clone... Sorry, get close to the microphone. Clone the repo into your Plugins directory, please. I'll give you a minute or two to do that. Everyone got the repo? Not yet. Okay, into your WP Content Plugins folder of your WordPress installation. Okay, those of you that have got it already, if you activate the plugin in the WordPress admin, well, let's just have a quick look through what we've got in that repository. So you've got the PHP file, the WCEU FAQ PHP. You've got a CSS folder with a WCEU FAQ styles.css file. You've got a workshop stages folder and a workshop notes folder. The workshop stages folder has... I've broken the workshop down into five stages and each of those folders has the project as it will be at that stage. So if anything doesn't work at some point, say at stage two it's not working and you can't move on to stage three, you just copy everything from stage two folder into your root directory and rebuild and it should all start working again. It might also be a good idea to actually open up the repo in a browser. So forget the git clone bit. Just open up the repo in a browser tab because then you can access the notes as well and you can copy and paste the code from the notes into, as you build the project, instead of having to type everything out that you're free to type if you want to. And you'll also be able to see the notes that I'm actually reading from here. So if you open up the repo and then go to the workshop notes folder, we'll come down to section zero but there's nothing in there that you need at the moment. Just so you can use that as a reference and then you can also use it to copy and paste the code snippets from. So in the workshop stages folder for stage zero, you'll see a WCEU workshop.xml file. Now that you have the plugin installed and activated, import the xml file into your WordPress installation. In case anyone needs a hint, in the tools menu, there's an import. And if you haven't done an import before on this particular WordPress installation, you'll need to install a plugin but it prompts you to do that. I'm sure you've all done this before. Import the xml file. WCEU workshop.xml. Import that. So go to tools, import. And it will prompt you through so if you need to install the importer plugin. That just gives you some demo content that we can work with. So what you should see now in the left hand sidebar of your WordPress admin is an FAQ menu option and if you click on that, you should see five or six FAQs that you've just imported. Do you all see that? Anyone not see that? Okay then if you create a new post or page, it doesn't really matter. And then, sorry, let me just head over to the next slide. Sorry, I had all that on the next slide anyway. Create a new page or post and put two short codes in as illustrated there. Yes, in your post or page you'll need a short code block and then put that short code into the short code block. You're all using the block editor, yeah? You're all using the classic editor. Good to know. So you're going to create two short code blocks one with the first short code and one with the second short code that has a category. Then save your post or page. I'll just say post from now on because everything's a post in WordPress. Save your post and then go and look at it in the front end. You should see that your first block of FAQs will have all five or six FAQs and the second one will just have I think it's four from the from a specific category. Everyone seeing that? Everyone with me? Awesome. Right, let's go have a look at WCFAQPHP in the root directory of the plugin and let's just have a quick look at it. You can see that it implements a custom post type to store each FAQ. So that's fairly straightforward. It also implements a custom taxonomy called WCFAQCAT. Then there's the short code function itself which checks if there's a category in the short code creates the orgs array that's going to be passed to WP query if there's a category it adds a taxonomy query to the orgs array and then runs a WP query to go and fetch the FAQs and then there's a show FAQ variable which and the markup is basically rendered into that variable and that is then echoed and there's some housekeeping stuff there as well. There's a function running that's what renders on the the front end and there's also a check for short code function because we're enqueuing a CSS file if we just enqueued it it would appear it'd be downloaded for every page whether there is an FAQ short code in the page or not. So this just checks short code and only enqueues it if the short code is found so if the short code isn't on a post then that's not enqueued and that just makes everything more efficient. So very basic, very simple short code plugin that implements a custom post type. Right. Let's get started on building the building the block. Everyone with me? Excellent. Right. In the root of your plugin, so in the same directory that WCFAQPHP is run this command. What this command does, it runs the WordPress create block scaffolding tool which scaffolds a block. Because we already have a plugin WordPress create block will normally scaffold a full plugin with a PHP file we've already got that so we don't need the full plugin scaffolding so we specify no plugin switch and we're going to be building a dynamic block so we specify variant dynamic and then the last bit WCFAQ block is going to be the name of the block. What NPX does, it kind of fetches the NPM package remotely executes it in memory and then removes it so you don't actually have to have that NPM package installed. In the same folder as where you have WCFAQPHP run it in that directory inside the plugin directory so inside WP content plugins whatever the plugin is called WCEUFAQ I think the block is inside the plugin yes so you run that command from the same directory as the WCEUFAQPHP file is it's super simple if they can assign it to a couple of categories as well yes if you've had trouble doing the import of the XML file just put three or four FAQs in and two categories and assign them to the a couple of FAQs to each category right so we've all got the scaffolded block so if you look at this so what you'll now have in addition to WCFAQPHP and the CSS folder you'll now have a new folder called WCEUFAQ block yes in there you've got six files block.json, edit.js editor.scss index.js render.php CSS if you open block.json oh hold on open block.json and this is just largely cosmetic stuff but just change a few of the of the properties in the in block.json to what you see up there of the repo yeah thank you let's move on to the next step I want you to create a package.json file again in the root so in the same directory as the WCEUFAQ.php and and populate that file with that you can copy it if you've got the repo open go to workshop notes section1.md and you can just copy that block from there so to do that just as a reminder go to the repo open the workshop notes folder and section1.md and you can copy the about halfway down that page it's the third code block you can just copy and paste that into a new package.json file in the plugin folder the same directory as WCEUFAQ.php okay we're all caught up there's one more step to do and that's register yep we've done that register the block so this goes in the WCEUFAQ.php so the same file that the shortcode is implemented in so where those functions that we looked at earlier in that at the bottom of that file so below the shortcode function so below the line that says add shortcode type this or copy and paste this from the note section1.md this is the last code block on that page this is the bit that actually registers the block so what do we have here we have an action hooked onto the init hook that runs the register block function and that runs register block type passes it the build directory you haven't got the build directory yet that's the next step but all the JavaScript and react code for the block will run from the build folder and that's what this is doing telling it to register a block that's contained in the build folder or that will run from the build folder right make sure you've saved all your changed files and then run from the command line again from that same directory run npm install and then that will give you a node modules folder and then you can run npm run build and now once you've run npm run build you should be able to go into your page your post again and you should now be able to add a wc eu faq block you can just add it below the shortcode blocks if you wish or create a new post that just has the block on oh of course so you're still on that stage are you? npm install okay we'll wait okay while we're waiting for npm install to run let's have a quick look at package.json the most important thing here is the scripts your um the most important ones there are start and build so I've really asked you to run build but we haven't got to that stage yet and then start we'll use a bit later so build is used when you want to build your final version and start script runs like a watcher that keeps the watcher any changes to your files and automatically builds so we'll be doing that in the next step so we don't have to keep running npm run build every time we make a change to our files and then the only other thing is the dependencies uses wordpress scripts and that's pretty much all that's happening in package.json npm run build will actually build your thing they both actually do the same job they both build the project for you into the build folder um only use build to build your final project when you're ready to deploy start is used during development because it implements a watcher which watches for changes in the file and automatically builds whenever it changes so we'll be using that as we go through the development but we're just doing a quick build now so we can get something into our editor and we can see that we've got a working block so are we still all on npm install it's running already oh right so if you tether your phone use 4g it comes in quicker there you go if you're still waiting so when npm install has finished do npm run build and then add a new wceufaq block into your page I really should have named that differently because wceufaq is a bit of a mouthful okay has everyone been able to add their block to their post anyone not been able to do that yet at the back there anyone else still npm installing okay who's still npm installing and who can see their block so about 3 or 4 people who can see the block in their editor and who didn't put their hand up to either question because that wasn't everyone for those of you that can see the block in the editor at the moment all you'll see is a blue block that says hello from the editor and in the front end you'll see a blue block that says something similar hello from a dynamic block the plugin of the plugin folder yep but the plugin anyone still npm installing here whoa so if you're ever in any doubt about where a file goes you can always compare it to the to the stage that we're at so you can always compare your project to the state workshop stages stage one folder and your project should look like that how's the npm install going oh dear so just 2 people we're just waiting on 2 oh gosh didn't anticipate that the install process would take so long so apologies to those who are at that stage already and are still waiting we'll give them a couple more minutes to catch up okay how are we doing with the npm install good there good there anyone still waiting one person just one person still waiting we'll wait okay second 2 so if you're following along on the repo go to workshop notes section 2.md in this section we're going to render the FAQs in the front end now earlier we built a dynamic block there's 2 kinds of blocks a static block and a dynamic block what a static block does is it uses an edit function to render the content in the editor and a save function to the WordPress database which then gets rendered in the front end what a dynamic block does the editor is pretty much the same for a static block an edit function renders in the editor but it uses PHP to render the front end and we're using a dynamic block because if somebody adds a new FAQ custom post type to then the PHP will dynamically fetch it without you having to go into the editor and update the block so we created a dynamic block so we're going to separately do the front end part in PHP and then later on we'll do the editor part in JavaScript React so because we've already got our short code in PHP we can kind of reuse that it's pretty much the same code that we're going to use in the from the short code function and we're going to use it in the block to render the front end and we're going to use render.php if you look in the the WCFAQ block folder where all the where your edit.js and your block.json was that you edited earlier there's a render.php file what you would normally do is copy your short code function across or the contents of the short code function and edit it but what you can do here is you can just copy the code from here and you'll see it's virtually identical there's just a couple of changes in place of the hard coded class in the WC EU FAQ PHP file where instead putting get block wrapper attributes which will dynamically put a class in and we're also going to be using that later on to add some some dynamic CSS that the user can change but for now all it's doing is putting the class onto that div and the only other change from the short code function is we've removed the tax query at the moment so for now this will just render all the all of the FAQs we haven't got the facility at the moment to get FAQs from a specific category okay once you've got that file created save it and then run npm start and as I hinted at earlier what npm start does it does pretty much the same as npm build it actually builds the project from your working directory into the build directory but if you relied on npm build you'd have to every time you made a change to a file you'd have to run that command and that would get pretty tired pretty quickly so npm start runs a watcher and kind of automates that process for you every time you make a change it'll automatically run the build process so you can get on with coding and whenever you make a change or whenever you save a change the watcher runs the build and then you can check your change in the editor or the frontend without having to run the build manually so if you've got your render.php function and you've run npm start if you go to your frontend of where you've put the the block which you previously showed a little blue box was a little blue box with some text in you should now see all the FAQs who's not seeing that yeah all good okay we'll move on okay so let's show the FAQs from a specific category add this just above well or before the wp query runs yes you'll need to add it after the args array is defined and before the wp query is called so at the moment this is just going to this is just a hard coded query to get a particular taxonomy term if you save the file again you'll find the build will run automatically so if you watch in your terminal you should see the build rather than it might just flash by and then if you check your frontend again you should just see the FAQs from that category everyone got that okay excellent how's the pace too slow nope okay I will speed things up then okay so at the moment we're just treating the FAQs from a particular category so let's make our first steps to making the category user configurable we need to add an attribute block.json so in block.json in the wcfaq block directory at the bottom well block.json is an object contains an object and your attribute will be the final object in that well with the final property and that object so you put it just above the closing bracket of the object you'll need to add a comma after the previous one and the thing with block.json is it's very strict about commas you can't have a trailing comma so watch out for that if you have a trailing comma in block.json the compiler will bomb out and if you look in the terminal you'll get lots of red text and you'll be returned to the command prompt and you have to run npm start again after you've fixed the error in block.json you'll end up in an endless loop sorry I forgot to change the slide that's what you add this is the attribute you add to the end of block.json again you can copy and paste it from section2.md then with that attribute in place in block.json let's use that attribute in render.php so change out the previous tax query to this where you're using attributes all your attributes that you define are automatically available to you in render.php so any attribute that you define in block.json you can use in render.php but what we're also doing here is we're checking like we did in the shortcode function we're checking if category exists first before we add the taxonomy query the arguments that get passed to wp query you should see in your front end because we haven't made any changes to the editor yet you should see in your front end it's exactly the same because the default category that we've used in block.json for the attribute is the same as we had hard coded earlier so what you can now do is go into block.json and change your default to something else the other category if you're using if you imported the XML file is Vienna no not yet now you have to go into block.json and change it from Athens to Vienna you can just remove the default or put an empty string there or just not have the default property at all but if you remove the default you need to remove the trailing comma after type string because jason doesn't like trailing commas so try that try changing your attribute to Vienna and see what you get in your front end and as this gentleman suggested try removing it completely and you should get all your FAQs in the front end try even changing it to a non-existent category like Paris which if you're using the XML file doesn't exist and see what happens I've got to admit I didn't actually try this myself but my guess is you'll get a no post found we'll quote up remove what sorry the whole default did you remove the trailing comma and you've got an error if in doubt compare your code to the workshop stage 2 folder because this is the stage we're at now your project should now look identical to the stage 2 folder in workshop stages is everyone else getting the behaviour I'm saying if you change that to Vienna you just get one or two posts if you change it back to Athens you get all of them all of the Athens ones if you remove it completely you get all the posts or if you put a category that doesn't exist you get no post found everyone getting that awesome on to section 3 then let's render the FAQs in the editor this is where we're really making progress to implement the kind of whizzy wig functionality that users are used to so instead of seeing a code a short code block that rather boring looking thing they will actually see in the editor what is rendered in the front end right so now open edit js in the wcfaq block directory edit.js at the top of that file you'll see a number of import statements you can leave those alone but add a new import statement that we're working now with workshop notes section 3.md if you just want to copy and paste stuff and this is the first code block in the section 3.md so just put that in below all the other import statements so use entity records react hook that fetches the that will fetch data from the WordPress database using the REST API so it's provided in the core data package so we import it and destructure it from the core data package okay next replace the entire edit function that you see there I think it's only about 3 or 4 lines at the moment replace that entire edit function with this and this is a good time to have your is to just copy and paste it from the section 3.md file because that's, oh did I did I change the slide that's the slide, apologies for that trying to kind of working with two screens here so let's take a look at what's going on here so we're using the use entity records hook that we imported earlier and we're telling it that we want to get records of a particular post type and the post type we want is WCEU FAQ our custom post type that we defined in the in the main plugin file and we're storing that in FAQs so we'll have an array of posts in FAQs then then we're just returning a basically we're just rendering the markup use block props is a hook that puts props onto the containing element in this case a div is a containing element at the moment it's just putting the class on much in the way that we did in render.php but again later on we'll be using it for some of our own CSS to spread that onto our containing element then we're checking whether we've got FAQs what you could do if you want is put a console.log underneath the const FAQs use entity records just to see what you've got in FAQs and have a look in the console you see FAQs will have an object that has two or three things that report the status has resolved or is resolving and then it has a records property which stores the records and if you do put a console.log you'll see that initially it'll say is resolving is true and the records array is empty and eventually is resolving to changes to false has resolved changes to true and your posts are then resolved property in an array so we're checking whether there's anything in FAQs.records if there is then we're going to use the JavaScript array.map function to iterate over them and just return the content the title and the content in a detail summary element just like render.php does and the original shortcode function does and the dangerously set innerHTML just means that if there's any if you're using any angle brackets or something in your content we're not in the demo content but if there was they would be rendered instead of being ampersand whatever the element and the section has a class name which you'll see render.php and the original shortcode function had that and we'll be using that later on to individually style each each block okay are we all there? yes if is resolving is true it's waiting for the records to come in from the database so it's waiting for the REST API to deliver the records has resolved will be false when the records have arrived then is resolving changes to false has resolved is true and your records should be or your posts should be in the records you can you could use it to put a spinner so you could say if is resolving if is resolving put a spinner in show a spinner so actually I should have added that to the project it's like one line of code well you need to import spinner and it's one line of code but I'll leave that as an exercise for homework put a spinner in while you're waiting for the data to come in it's easy if is resolving show the spinner which you need to import okay sorry just catching up with my notes okay right at this stage you should now if you go into your editor post in the editor as well all your FAQs in the editor in an expanding summary detail summary yeah but it still doesn't look like what you see in the short code because because it's not styled yet but we'll come to that right the next stage then is to get the FAQs of a certain category so at the moment we're just seeing all of the FAQs so change that line where it says FAQs the use entity records to put an extra parameter which is an object saying we want posts from the WCEU FAQ cat taxonomy with the ID4 I'm really regretting we're getting this naming scheme now WCEU FAQ cat well actually it was for for my WordPress what you might need to do is go into your WordPress admin and check what the ID is for your two categories in there because when you imported it it might have assigned different IDs so it might not be for so check your category IDs first and change it to whatever category ID you want to show everyone happy with finding the category ID ok don't do anything yet because once you've got the category ID and put it there in place of the four no sorry that's fine that's fine if you should now be able to see in the editor you know the the FAQs from that particular category and if you've got two categories try changing it to the other category in this code block and you should see the FAQs from the other category as well yeah I think it does but I think it does work anyway yeah but we are going to change it to an integer next just to ok so let's let's actually use the attribute instead so now because we're having to use the ID instead of the slug which we used in the shortcode function change the attribute to this so we're going to type to integer instead of string and we're going to put three sorry we're going to put whatever ID corresponds to your category in my case it was three and then we can change the ah hold on have I missed a step here sorry bear with me just a second no I haven't missed a step ok now because we're using an ID instead of the slug we're going to need to change our tax query in render.php so instead of using field slug we need to continue to change that to field term ID in order for our front end to keep to work correctly ok and then we'll do the same in or something similar in edit.js we're going to get that attribute now that it's an ID instead of a slug what we need to do in render.php the attributes are kind of automatically available in the edit function we need to destructure the attributes from the object that gets passed to the edit function so the first line of the edit function just destructure attributes in the parameters and then once we've got the attributes object we can destructure category from it at the moment that's the only property that the attributes object has because it's the only attribute we've defined and then we can use it in place of our hard coded category the last line there and then if you go and change it in block.json to the other category ID it should change in the editor and in the front end so you're getting that behaviour now if you update the block.json to the two different IDs both the editor view and the front end view the content changes that so now let's make our block look like our original short code and we'll just put all of that into style.scss so our original short code function will still use the old css file but the block for both the front end, the render.php and the edit function for the editor will use this css which at the moment is identical to the css that the short code function is using but that's going to change so if you did as I suggested earlier and added your short code block underneath rather than the okay the block that we've just created the wcufaq block if you've added that block below the short code block where you type the short code in now both blocks should look both sets of FAQ in the front end should look the same with the same colour scheme all getting that amazing it's going to section 4 where we're actually going to make so at the moment we're having to change the category in block.json the ID there in order to have different sets of so suppose we want one block to show FAQs about Athens and the other block to show FAQs about Vienna we have to hard hard code well we can't do that at the moment but you know it's hard coded you know in block.json there's no way to actually do it apart from editing block.json which isn't very user friendly for your average content editor so we're going to and this is where you know as I said earlier we can add functionality to a block that makes it more user friendly than a short code so for a short code the user would have to add that attribute so the short code category equals and they'd need to know the category slug for the short code so we're going to make this easier for the user by putting all the categories in a dropdown so when they add a block an FAQ block they've got a a dropdown select element that they can choose the category from and they don't need to know the names of the categories or the IDs of the categories so that's what we're going to do in this section I don't know why I suddenly skipped a load of slides there right let's change the default to 0 this is in block.json by the way and now because the category might be 0 we only want to conditionally add the query to our use entity records so we're still going to destructure our category from the attributes and then we're going to check the value of category if it's not 0 so this is a ternary conditional I hope you've all come across that before so if category is not 0 so if it's an ID of a category then it will do it will return that object which is the same as what we previously had where it says query there otherwise it will return an empty object you could actually return null there as well and so use entity records will either fetch the post of the post type WCAQ with no query if there isn't a category or if category is 0 which is the default or it will use the category object there WCAQ category in place of query there I'm sure you all understand what's going on there so you can try that if you like actually let's not do that let's now start making the category user selectable so the next thing we're going to do is we're going to add an element a select element to the inspector panel the inspector panel is the right hand sidebar in the block editor where you often get controls for changing colour and so on so we're going to add a select element to that that is going to contain a drop down with the categories that the user can select but we've already got a div which is what the what editor returns to render in the editor and we can't have more than one root level element in a react component so what we're going to do here we're going to add what's called a fragment wrapper which is basically just empty HTML element at the top there you've got two angle brackets just like any HTML element but it's empty and then a closing one at the bottom there so just wrap the entire div in these fragment elements fragment element sorry singular okay so now we've got a new root level element and we can now add elements within that alongside the div element so we're going to add some elements there so we need to import some components so we need to import inspector controls from the block editor and we need to import panel body and select control from components so just add those at the top along with your other import statements I don't think I'm pretty sure you can't use an import twice from the same thing so add you've already got import use block props and wordpress block editor so you have to put inspector controls in there as part of that okay once you've got those imported are we ready to move on from this slide yeah once you've got those imported we're now going to add those components to to our edit function inside the wrapper inside the fragment just so above the div add the inspector controls element inside the inspector controls you've got a panel body and inside the panel body you've got a select control inside the fragment above your div element where you're rendering the content so if I go back so you added a fragment to wrap your div element and then just above the div element and underneath the opening fragment you would put that so it's illustrated there you've got your opening fragment put your inspector controls and panel body and select control and then your div element which you've already got so you put it between the fragment opener and the existing div element so inspector controls will put it will add it to the sidebar panel where you're used to seeing all your colour editing stuff panel body just formats it nicely inside that inside the inspector panel and you can also use panel body if you've got lots of different controls you can categorise them and label them so you can use panel body for that as well and then inside that you have the actual select control where we're going to have our drop down with the different categories for the user to select so we've already previously got category we destructured it from attributes so we can give we can assign the category to the value so that the select control will display whatever the current category in attributes is and we have an on change function which we're going to come to so we've all got the inspector controls I think if you try and view it in the editor now I think you'll get an error because it'll complain that you haven't got an on change cat function so let's fix that oh sorry before we do that previously we had an empty options element what we need to do the options in there the moment we're just hard coding the options again the values will need to be the category IDs for your instantiation of wordpress not mine so the moment we're just hard coding that just to get it working again you just copy and paste it from section 4.md in fact if you copied and pasted it you'd have got that all both of those ok so the next thing to do is to add that handler function that on change handler so you can add that you need to put it above the return statement so my recommendation is to put that function immediately above the return now this isn't going to work yet so don't try it so if you recall from over here our select control had on change it would call an on change cat function which is what we've just implemented whatever the value has been changed to from the select dropdown gets passed to the on change cat function and then set attributes will change the category in the attributes and because we defined it as an integer we need to use the edit function to pass it to a number but this isn't going to work yet because we haven't got set attributes so that's also passed to the edit function within the object that gets passed to the edit function and so we can destructure it onto the edit function and that should all work now if you've got the correct ideas in your select element you should be able to change that and it will dynamically change in the editor it will save the post it will change on the front end and you can change the categories or have no category to I gave you a label all and you can select all categories as well what's gone wrong? the set attribute function updates the attribute so the default attribute no longer applies okay everyone caught up okay so at the moment let me just back up a couple of slides at the moment we just hard coded the options and you needed to go and check what your category IDs were let's make that more dynamic now let's actually fetch the categories so we're going to use entity records again but instead of a post type this time we're going to request a taxonomy and the taxonomy we're going to request is WCE WCEU FAQ cat which we defined in the original original plugin PHP file yeah we we we configured our post type and our custom taxonomy there and now we're asking use entity records which we've already imported and used once to fetch the posts of the FAQ post type now we're asking it to fetch all the posts in the taxonomy WCEU FAQ cat and to store it in cats and run a console.log cats just to see what you've got and just like when we got the posts you'll see has resolved is resolving and a records property and once it's once it's finished resolving and has resolved is true the records property you'll have if you've used the the XML file that from earlier you'll have two records there with the two taxonomy terms okay so let's start replacing the the array in the select element so let's create a new constant options we're going to check for records and if there are records just like we did for the posts we're going to map over them and return an object for each each of the taxonomies the category name and the category ID again you can put that anywhere in the edit function above the return where you've seen that? okay correct but I haven't got that far yet sorry but you are correct so I will point that out when I get there right so as I said this block of code can go anywhere in your edit function so long as it's after the call to use that to use that to use that to use that is after the call to use entity records to get the taxonomy and before the the return okay so now we can replace the static options we had before now we can statically have the all label because that's not a category we're not going to get that from my call to use entity records so we keep the label all and then we spread the options variable the options array that we just created here on to the rest and that dynamically populates options so if you add another category it will dynamically get added there and as that gentleman pointed out there's a typo it's not on change C cat it's on change cat and now from the select drop down in your inspector panel you should be able to select that down you'll see your categories and if you change them it'll dynamically and instantly update in the editor and if you save the post it'll change in the front end as well everyone getting that? amazing let's move on to section 5 we've got 20 minutes left so if you're following along with the notes open up section 5.md and we're going to do some more importing so as well as the use block props and inspector controls we're now going to import panel color settings from block editor okay and then we add that component into our jsx put it just beneath bear with me a second so at the moment put it immediately below your panel body so you've got your closing panel body tag put panel color settings immediately below that now there's two things to note here a value so we're going to need an attribute called question text color and once again we need a non-change function so let's start by adding the attribute so you put that immediately below your previous attribute which was category once you've got the attribute destructure it so alongside category where you've destructured category also destructure question text color from attributes so that makes question text color available to to our panel color settings component and then we also need the handler function which works pretty much the same as the other handler function just put it below the other handler function so once it's on a change you'll get the value passed to it and then you can use set attributes to change the question text color attribute in define in block.json to whatever value gets passed okay now all this will work and the attribute will be updated but nothing's going to happen because you can't because the CSS is still hard coded so the text color of the question is not going to change so let's fix that now let's create an FAQ styles object and what we're doing here is we're using a CSS variable or a CSS custom property and then assigning question text color which we destructured in the previous step so the value in the question text color attribute will be assigned to the CSS variable you're familiar with CSS variables normally CSS variables put at the root of a CSS file but you can actually put CSS variables in the scope of a particular CSS element like a class or an ID and that is essentially what we're doing here we're defining that CSS variable onto onto just the block so what we now need to do is remember I said earlier that used block props passes props onto our containing div and it was previously passing just the class now we're going to use that FAQ styles object that's got a the CSS variable we're going to pass that to use block props so it spreads that onto the div our wrapping div element will now have a CSS variable with the value of whatever is stored in the attributes and what we then need to do is actually use that CSS variable in our CSS so you see that far and then a CSS variable and that CSS variable only applies to that block because it's been spread onto just that div unlike what you might be used to whether a CSS variable applied to the root element in CSS now you should have in your inspector panel you should have a text color or question text color element that you can use to change the color of the text and you'll find that works fine in the editor but doesn't work in the front end yep everyone getting that so let's make that work in the front end as well so over in render.php create so similar to what we've just done in the edit we're going to create an FAQ FAQ styles variable so when PHP now so the syntax changes and it's going to have the same CSS variable name and as attributes are automatically available to render.php we can just assign the question text color attribute to that CSS variable so this is all very similar to what we did in JavaScript in edit.js I've put that on two lines because of the slide but you'd normally put that on one line if you're copy pasting from version5.md it's all on one line and then just in the way that we passed show the FAQ styles to use block props for the editor we also now pass it as a parameter to the get block wrapper elements are now containing div in render.php so this once again puts the CSS variable and makes it available just to that div and because we've already changed the style.css that should now any change you make in the editor to the text color of the question will now show up in the front end as well everyone getting that? We're short of time now so let's whiz through let's do exactly the same for the question background color so we need a new attribute in block.json my mistake this is a new color setting have I skipped a slide? sorry I've got these the wrong way round add a new attribute once you've got the new attribute we need to add a new color setting if you look at the panel color settings the color settings is an array of objects so just add the new question background color object there okay okay I've got 10 minutes so I'm going to move on okay I already did that now we need to destructure the attribute so alongside the previous attributes castering question text color we now need to destructure the question background color and then we add that to FAQ styles assigning it to another CSS variable question background color this is pretty much all the same as we did before so I'm kind of whizzing through this because of the time we still need the handler function so add that just beneath the other two handler functions so when you change the color it will update the attribute and now we just need to update the CSS where the details summary has a back we're using the CSS variable on the background color and now you should be able to change both the text color and the background color of the question so that works in the editor but not in the front end sorry did I not move the slide on yeah okay so we need to add the CSS variable to the background color in styles.scss and then to make it work in the front end we need to get that add the CSS variable to our FAQ styles and assign it the attribute value and now your new background color for your question will show up in the front end as well all good so let's do the same for the for the answers now let's add what we're whizz through this because it's all stuff we've done before now we just need two attributes one for the answer text color and the answer background color I'm going to whizz through and hope you're just copying and pasting the code from section 5.md now then you need to add a new we're going to add a new panel color settings so we're going to have two panel color settings in our code so you're going to have your panel body which contains your your category select control you've got one panel body panel color settings for the question colors and just below that we're going to add a new panel color settings for the answer colors and then just like the other one the one for the question you add an array of objects to define the value which it's going to come from the attribute and a non-change function which we haven't done yet and did we not destructure the attribute no we didn't destructure the attributes yet sorry I think there's five minutes left so that's fine okay I'll just wrap up really really quickly okay I'm going to whizz through this because this stuff we've done before create the handler functions for these if you want to catch up it's all in section 5.md which you can look at a bit later it's all in the repo create the handler functions destructure the attributes so the new attributes are answer text color and answer background color add them to FAQ styles so that they get spread by used block props onto the the wrapping div use them use the two new CSS variables in the details the color and background color and then in the in render.php we just keep adding the new custom variables to FAQ styles and that's me, that's my Twitter handle thank you very much