Adding a new page



  • My requirement was to add a map icon and the corresponding route /map besides the other NodeBB icons i.e. Users, Tags, etc. I was able to modify the code and add it.

    Now I want to display a map in the "/map" page with the corresponding backend storing the latitude and longitude etc. of a particular user. But I am stuck. I looked at the existing .tpl files and to my surprise, they belong to the node_modules folders.

    Could anybody pl. guide me what is the best way to address this requirement?

    Thanks


  • Global Moderator

    You want to create a plugin to do this. Take a look at nodebb-plugin-quickstart



  • Thank you for the reply. By creating a new plugin, I am still unaware about how to add/display a map icon besides the other standard NodeBB icons like Tags, Users, etc.

    I went through this example plugin but still not successful. Can you pl. guide me further?


  • Global Moderator

    You want to display a navigation icon? The easiest way is to just add a new custom item at ACP -> General -> Navigation.



  • No.. not only simple display but with lots of additional functionality.. When the icon is clicked, I need to show a map and allow the user to place a marker on it and then save the corresponding latitude/longitude in the db.



  • Thanks I am able to add a custom icon including the route. Now could you pl. let me know where (in which files) in the associated plugin I am supposed to write the logic for this route?



  • //My Map Plugin: library.js
    plugin.init = function(params, callback) {
    	var router = params.router,
    		hostMiddleware = params.middleware,
    		hostControllers = params.controllers;
    		
    	router.get('/map', hostMiddleware.admin.buildHeader, controllers.renderMapPage);
    	router.get('/api/map', controllers.renderMapPage);
    	callback();
    };
    

    When I browse this URL: localhost/map

    I get the error in /public/src/admin/admin.js
    Line Number: 122 -- Cannot read matches property of null I debugged it and the undefined is the matches variable.

    Are these routes correct?
    router.get('/map', hostMiddleware.admin.buildHeader, controllers.renderMapPage);
    router.get('/api/map', controllers.renderMapPage);


  • Global Moderator

    Yeah those should work. What is inside renderMapPage? The error you mentioned is a client-side error in the ACP, I can't think of any reason that would occur because of something you did, it's probably unrelated.



  • Thank you for your kind support, Pita.

    Controllers.renderMapPage = function (req, res, next) {
    //Render the templates/map.tpl
    res.render('map', {});
    };

    Kindly help me solve it.



  • I think admin.js is expecting a url something like this... /admin/plugin/map whereas in my case it is simply "/map" I may not be correct.

    Kindly note that when I click the Map icon (whose route is /map) things work fine. But when I browse by entering this localhost/map in the browser and press Enter, it throws a client-side error in admin.js file.


  • Global Moderator

    Oh, sorry, I missed that issue. It should be hostMiddleware.buildHeader, not hostMiddleware.admin.buildHeader. Remove the admin part, as it tells the server to render map as part of the admin control panel.



  • You are awesome. It worked. Thanks once again.

    So I will place my third-party client-side JS libraries in static/lib (alngside main.js) And the system will minify/uglify them. Right?



  • My map.tpl
    <div id="mapid" class="map"></div>

    My plugin.json
    "scripts": [
    "static/lib/main.js"
    ],

    My main.js

      $(document).ready(function() {
    requirejs(["leaflet"], function(L) {
    
    		var map = L.map('mapid', {
    			attributionControl: false
    		}).setView(initialLocation, 12);
    

    ...

    Error: leaflet Uncaught Error: Map container not found.

    The <div id="mapid"> must be added to the DOM before calling L.map('mapid').

    This jquery reaady function is called after the DOM and page (map.tpl) are loaded. But still getting error. Where am I wrong?

    Kindly help me.


  • Global Moderator

    The way you have it there, it will run on every page. I'd suggest checking ajaxify.data.template.map (a boolean) before running those things.

    You might try putting a debugger; statement in there before the require call and check that the map is actually in the DOM when you expect it to be.



  • if(ajaxify.data.template.map == true) {

    requirejs(["leaflet"], function(L) {
    

    ...
    }

    It returns undefined everytime including when I click the map icon. It returns true only when I enter this URL: localhost/map and press Enter. When it returns true, the "Error: leaflet Uncaught Error: Map container not found." is still there.

    I will use the debugger; and see what it reports.



  • Using the debugger statement indicated that the map is not in the DOM



  • Any answers?


  • Global Moderator

    So if the map element isn't in the DOM, there's probably something wrong with your template. Check it, make sure it is correct. Check the built template in nodebb/build/public/templates to make sure it is correct.



  • The map.tpl has just one line. And the map.tpl in the build directory is simply a replica of my map.tpl.


  • Global Moderator

    Ok, and when you go to /map directly, that is, not from another link on your site, is the map element in the source for the page?


Log in to reply
 


Star

Looks like your connection to NodeBB was lost, please wait while we try to reconnect.