Simple Machines Community Forum

Customizing SMF => SMF Coding Discussion => Topic started by: vampirefrog on November 27, 2022, 06:48:09 AM

Title: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: vampirefrog on November 27, 2022, 06:48:09 AM
Hello, I've tried reading the documents (https://wiki.simplemachines.org/smf/Add_a_custom_action_using_integration_hooks) that I was able (https://wiki.simplemachines.org/smf/integration_hooks) to find, but there doesn't seem to be a simple tutorial that takes you from the first steps to adding some basic functionality. Neither of those two pages I linked to mention what files you need to modify, or where you need to create new files. So I find this very confusing, and I'm here to ask this very question, with some clarifications:

I am trying to insert a <script> (and a <link rel="stylesheet">) tag at (or near) the end of some pages, and I'd like to do this in an upgrade-proof way, so that when the forum version is updated, the code sits in a separate file, unaffected by any modifications that the base forum files might suffer.

In phpbb3, there is an includes/hooks folder where you can place your php files and the forum executes them, and in wordpress there is a wp-content/plugins folder, and I am assuming there is something similar in smf, or perhaps something that requires minimum or no modifications to the core files?

Before, I used to modify Themes/default/index.template.php, the template_body_below function, but I'm assuming there is a non-invasive way to do it.

Sorry to be so wordy, but I failed to find a starter tutorial for such a simple modification.

Thanks!
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: Kindred on November 27, 2022, 08:19:25 AM
Global header and footers mod?
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: vampirefrog on November 27, 2022, 09:11:33 AM
That would just add a dependency on a mod that could become obsolete sooner or later. The mod's page (https://custom.simplemachines.org/index.php?mod=351) doesn't even mention 2.1.3, so I'd be adding a liablity to my code that, if I update again, the mod would not be compatible anymore, and it wouldn't work anymore.

Is there a clean way to do this, without modifying any of the forum files?
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: vampirefrog on November 27, 2022, 09:17:16 AM
Let me add some more info, I need the injected HTML to be visible only on some pages, and only if the user has a certain permission. Therefore global headers and footers won't help because it doesn't have a condition like that.
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: m4z on November 27, 2022, 11:48:42 AM
Depending on what the "some pages" are, you could (ab)use a Portal mod for that. I use TinyPortal to add some required-by-law-for-German-websites links to the footer of my front page, but it's quite cumbersome to setup:

* Frontpage
  -  What to display on frontpage: Go directly to forum index
  - How frontpanel will be shown with content: Hide frontpanel, unless otherwise selected.
  - Additional panels to display on frontpage: deselect all but "Display bottom panel"
  - Save
* Blocks
  - deactivate all
  - add bottom
  - Title: "Registrierungsvereinbarung, Datenschutz, Impressum"
  - Choose type of block: "Code: BBC"
  - Save
  - Status: On
  - Content: [url="index.php/?action=agreement"]Registrierungsvereinbarung und Datenschutz[/url]  [url="impressum.php"]Impressum[/url]
  - Choose style for the block: catbg+windowbg2
  - Allow block to collapse: Do not allow block to collapse
  - Save
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: shawnb61 on November 27, 2022, 11:56:39 AM
If you want a new theme, I would clone the theme in the admin control panel & update index.template.php.  Patches will attempt to update the new theme, so you will be basically patch-proof within 2.1.x. 

If you want the changes to be independent of any one theme, you are looking for a mod.  Two approaches.  You could either find a very simple mod and strip it down to one integrate_load_theme hook.  You can start with something like:
https://custom.simplemachines.org/index.php?mod=4336

Or you can use Bugo's excellent generic mod builder to accomplish much of the same:
https://custom.simplemachines.org/index.php?mod=4321
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: Sesquipedalian on November 28, 2022, 11:32:49 AM
Yes, Bugo's generic mod builder will help you with all the infrastructure you need to create a mod.

As for the task of inserting the JavaScript and/or CSS, you can use the whichever of the following functions in Load.php is the most appropriate for your purposes:


Once you have used Bugo's mod builder to set up your mod, including one or more integration hook functions, you can call those functions from inside your mod's code in order to load whatever you need.

Since you only want to load your custom JavaScript and CSS on certain pages, I suggest looking through the SMF code that creates those pages in order to find integration hooks that are specific to those pages, and then hooking your mod into those. 

The other option would be to hook into an early, generic hook like integrate_load_theme, but then your function would need to do a bunch of logic itself to figure out whether it should load your custom JavaScript and CSS. This would be more work for you and more likely to have unintended side effects than my recommended approach.

If you want recommendations for specific integration hooks to use for your purposes, you will need to tell us more about which pages you want to load this custom JavaScript and CSS on.
Title: Re: Simple upgrade-proof code to inject a js tag at the end of some pages?
Post by: vampirefrog on November 28, 2022, 02:27:58 PM
Thanks for the replies, guys. I'll take a look when I get some more time.

I'm basically adding a chat box that's connected to a socket dot io server, and I want that to pop up only on the front page, and the forum and topic pages. In effect, not in the private messages, or any of the backend pages.