mirror of
https://github.com/next-theme/hexo-theme-next.git
synced 2026-01-17 18:22:33 +00:00
Refactor sub-menu (#492)
This commit is contained in:
parent
72c28e5e87
commit
e16688573b
@ -1,13 +1,10 @@
|
||||
{% macro render(name, itemName, value) %}
|
||||
{% macro render(node) %}
|
||||
|
||||
{%- set itemURL = value.split('||')[0] | trim %}
|
||||
{%- if not itemURL.startsWith('http') %}
|
||||
{%- set itemURL = itemURL | replace('//', '/') %}
|
||||
{%- endif %}
|
||||
<li class="menu-item menu-item-{{ itemName | replace(' ', '-') }}">
|
||||
{%- set itemURL = node.path %}
|
||||
<li class="menu-item menu-item-{{ node.name | lower | replace(' ', '-') }}">
|
||||
|
||||
{%- set menuIcon = '<i class="' + value.split('||')[1] | trim + ' fa-fw"></i>' if theme.menu_settings.icons and value.split('||')[1] else '' %}
|
||||
{%- set menuText = __('menu.' + name) | replace('menu.', '') %}
|
||||
{%- set menuIcon = '<i class="' + node.icon + ' fa-fw"></i>' if theme.menu_settings.icons and node.icon else '' %}
|
||||
{%- set menuText = __('menu.' + node.name) | replace('menu.', '') %}
|
||||
|
||||
{%- set menuBadge = '' %}
|
||||
{%- if theme.menu_settings.badges %}
|
||||
@ -18,7 +15,7 @@
|
||||
}
|
||||
%}
|
||||
{%- for menu, count in badges %}
|
||||
{%- if name == menu %}
|
||||
{%- if node.name == menu %}
|
||||
{%- set menuBadge = '<span class="badge">' + count + '</span>' %}
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
|
||||
@ -3,23 +3,8 @@
|
||||
{%- if theme.menu or theme.algolia_search.enable or theme.local_search.enable %}
|
||||
<nav class="site-nav">
|
||||
<ul class="main-menu menu">
|
||||
{%- for name, path in theme.menu %}
|
||||
{%- set respath = path %}
|
||||
{%- if path == '[object Object]' %}
|
||||
{# Main Menu (default menu item for Submenu) #}
|
||||
{%- for subname, subpath in path %}
|
||||
{%- set itemName = subname | lower %}
|
||||
{%- set respath = subpath %}
|
||||
{%- if itemName == 'default' %}
|
||||
{%- set itemName = name | lower %}
|
||||
{{ menu_item.render(name, itemName, respath) }}
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
{% else %}
|
||||
{# Main Menu (standard menu items) #}
|
||||
{%- set itemName = name | lower %}
|
||||
{{- menu_item.render(name, itemName, respath) | trim }}
|
||||
{%- endif %}
|
||||
{%- for node in theme.main_menu %}
|
||||
{{- menu_item.render(node) | trim }}
|
||||
{%- endfor %}
|
||||
|
||||
{%- if theme.algolia_search.enable or theme.local_search.enable %}
|
||||
|
||||
@ -1,92 +1,12 @@
|
||||
{% import '_partials/header/menu-item.njk' as menu_item with context %}
|
||||
|
||||
{%- if theme.menu and is_page() %}
|
||||
{# Submenu & Submenu-2 #}
|
||||
{%- for name, value in theme.menu %}
|
||||
{%- set respath = value %}
|
||||
{%- if value == '[object Object]' %}
|
||||
|
||||
{# If current URL is value of parent submenu 'default' path #}
|
||||
{%- set currentParentUrl = page.path.split('/')[0] | trim %}
|
||||
{%- if currentParentUrl == value.default.split('||')[0] | trim | replace('/', '') %}
|
||||
|
||||
{# Submenu items #}
|
||||
<ul class="sub-menu menu">
|
||||
{%- for subname, subvalue in value %}
|
||||
{# For main submenu items #}
|
||||
{%- if subvalue != '[object Object]' %}
|
||||
{%- set itemName = subname | lower %}
|
||||
{%- if itemName == 'default' %}
|
||||
{%- set parentValue = subvalue.split('||')[0] | trim %}
|
||||
{% else %}
|
||||
{%- set respath = subvalue if subvalue.startsWith('http') else (parentValue + subvalue) %}
|
||||
{{ menu_item.render(subname, itemName, respath) }}
|
||||
{%- endif %}
|
||||
{% else %}
|
||||
{# For 'default' submenu item in main submenu #}
|
||||
{%- set itemName = subname | lower %}
|
||||
{%- for subname2, subvalue2 in subvalue %}
|
||||
{%- if subname2 == 'default' %}
|
||||
{%- set respath = parentValue + subvalue2 %}
|
||||
{{ menu_item.render(subname, itemName, respath) }}
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
</ul>
|
||||
{# End Submenu items #}
|
||||
|
||||
{# Submenu-2 #}
|
||||
{%- for name, value in theme.menu %}
|
||||
{%- set respath = value %}
|
||||
{%- if value == '[object Object]' %}
|
||||
|
||||
{%- for subname, subvalue in value %}
|
||||
{%- set itemName = subname | lower %}
|
||||
{%- if itemName == 'default' %}
|
||||
{%- set parentValue = subvalue.split('||')[0] | trim %}
|
||||
{%- endif %}
|
||||
{%- if subvalue == '[object Object]' %}
|
||||
|
||||
{# If current URL is value of parent submenu 'default' path #}
|
||||
{%- set paths = page.path.split('/') %}
|
||||
{%- if paths.length > 2 %}
|
||||
{%- if paths[1] == subvalue.default.split('||')[0] | trim | replace('/', '') %}
|
||||
|
||||
{# Submenu-2 items #}
|
||||
<ul class="sub-menu menu">
|
||||
{%- for subname2, subvalue2 in subvalue %}
|
||||
{%- set respath2 = subvalue %}
|
||||
{%- set itemName = subname2 | lower %}
|
||||
{%- if itemName == 'default' %}
|
||||
{%- set parentSubValue = subvalue2.split('||')[0] | trim %}
|
||||
{% else %}
|
||||
{%- if subvalue2.startsWith('http') %}
|
||||
{%- set respath2 = subvalue2 %}
|
||||
{% else %}
|
||||
{%- set respath2 = parentValue + parentSubValue + subvalue2 %}
|
||||
{%- endif %}
|
||||
{{ menu_item.render(subname2, itemName, respath2) }}
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
</ul>
|
||||
{# End Submenu-2 items #}
|
||||
|
||||
{%- endif %}
|
||||
{%- endif %}
|
||||
{# End URL & path comparing #}
|
||||
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
{# End Submenu-2 #}
|
||||
|
||||
{%- endif %}
|
||||
{# End URL & path comparing #}
|
||||
|
||||
{%- endif %}
|
||||
{%- set menus = next_menu(page.path) %}
|
||||
{%- for menu in menus %}
|
||||
<ul class="sub-menu menu">
|
||||
{%- for node in menu %}
|
||||
{{ menu_item.render(node) }}
|
||||
{%- endfor %}
|
||||
</ul>
|
||||
{%- endfor %}
|
||||
{# End Submenu & Submenu-2 #}
|
||||
{%- endif %}
|
||||
|
||||
@ -1,18 +1,27 @@
|
||||
{%- set paths = page.path.split('/') %}
|
||||
{%- set count = paths.length %}
|
||||
{%- if count > 2 %}
|
||||
{%- set link = '' %}
|
||||
{%- set link = '/' %}
|
||||
<ul class="breadcrumb">
|
||||
{%- for path in paths %}
|
||||
{%- if path != 'index.html' %}
|
||||
{%- if loop.index == count and path.endsWith('.html') %}
|
||||
{%- set link = link + path %}
|
||||
{%- else %}
|
||||
{%- set link = link + path + '/' %}
|
||||
{%- endif %}
|
||||
{%- if theme.menu_map.has(link) %}
|
||||
{%- set name = __('menu.' + theme.menu_map.get(link).name) | replace('menu.', '') %}
|
||||
{%- else %}
|
||||
{%- set name = path %}
|
||||
{%- endif %}
|
||||
{%- if loop.index == count - 1 and paths[loop.index] == 'index.html' %}
|
||||
<li>{{ path | upper }}</li>
|
||||
{% else %}
|
||||
{%- set link = '/' + path if link == '' else link + '/' + path %}
|
||||
<li>{{ name | upper }}</li>
|
||||
{%- else %}
|
||||
{%- if path.endsWith('.html') %}
|
||||
<li>{{ path | replace(r/\.html$/, '') | upper }}</li>
|
||||
{% else %}
|
||||
<li><a href="{{ url_for(link) }}/">{{ path | upper }}</a></li>
|
||||
<li>{{ name | replace(r/\.html$/, '') | upper }}</li>
|
||||
{%- else %}
|
||||
<li><a href="{{ url_for(link) }}">{{ name | upper }}</a></li>
|
||||
{%- endif %}
|
||||
{%- endif %}
|
||||
{%- endif %}
|
||||
|
||||
@ -11,6 +11,8 @@ hexo.extend.filter.register('before_generate', () => {
|
||||
require('./lib/injects')(hexo);
|
||||
// Highlight
|
||||
require('./lib/highlight')(hexo);
|
||||
// Menu and sub menu
|
||||
require('./lib/navigation')(hexo);
|
||||
}, 0);
|
||||
|
||||
hexo.on('ready', () => {
|
||||
|
||||
57
scripts/events/lib/navigation.js
Normal file
57
scripts/events/lib/navigation.js
Normal file
@ -0,0 +1,57 @@
|
||||
'use strict';
|
||||
|
||||
const { join } = require('path').posix;
|
||||
|
||||
class TreeNode {
|
||||
constructor(parent, path, name, icon) {
|
||||
if (parent && !path.startsWith('http')) {
|
||||
path = join(parent.path, path);
|
||||
}
|
||||
this.parent = parent;
|
||||
this.children = [];
|
||||
this.path = path;
|
||||
this.name = name;
|
||||
this.icon = icon;
|
||||
}
|
||||
|
||||
append(child) {
|
||||
this.children.push(child);
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = hexo => {
|
||||
const menu_map = new Map();
|
||||
const main_menu = [];
|
||||
hexo.theme.config.menu_map = menu_map;
|
||||
hexo.theme.config.main_menu = main_menu;
|
||||
|
||||
function parse(menu, parent) {
|
||||
if (!menu) return;
|
||||
Object.entries(menu).forEach(([name, value]) => {
|
||||
if (name.toLowerCase() === 'default') return;
|
||||
let node;
|
||||
if (typeof value === 'string') {
|
||||
const [path, icon] = value.split('||').map(v => v.trim());
|
||||
node = new TreeNode(parent, path, name, icon);
|
||||
} else if (typeof value === 'object') {
|
||||
if (typeof value.default !== 'string') {
|
||||
hexo.log.warn('Missing default entry for menu item:', name);
|
||||
return;
|
||||
}
|
||||
const [path, icon] = value.default.split('||').map(v => v.trim());
|
||||
node = new TreeNode(parent, path, name, icon);
|
||||
parse(value, node);
|
||||
}
|
||||
if (node) {
|
||||
menu_map.set(node.path, node);
|
||||
if (parent) {
|
||||
parent.append(node);
|
||||
} else {
|
||||
main_menu.push(node);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
parse(hexo.theme.config.menu);
|
||||
};
|
||||
19
scripts/helpers/navigation.js
Normal file
19
scripts/helpers/navigation.js
Normal file
@ -0,0 +1,19 @@
|
||||
/* global hexo */
|
||||
|
||||
'use strict';
|
||||
|
||||
hexo.extend.helper.register('next_menu', function(path) {
|
||||
path = ('/' + path).replace(/index\.html$/, '');
|
||||
const { menu_map } = this.theme;
|
||||
if (!menu_map.has(path)) return;
|
||||
let node = menu_map.get(path);
|
||||
const menus = [];
|
||||
if (node.children.length) {
|
||||
menus.unshift(node.children);
|
||||
}
|
||||
while (node.parent) {
|
||||
menus.unshift(node.parent.children);
|
||||
node = node.parent;
|
||||
}
|
||||
return menus;
|
||||
});
|
||||
Loading…
x
Reference in New Issue
Block a user