mithril-materialized 3.4.5 → 3.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/advanced.css +141 -2
- package/dist/components.css +141 -2
- package/dist/core.css +126 -126
- package/dist/forms.css +126 -126
- package/dist/index.css +269 -128
- package/dist/index.esm.js +231 -18
- package/dist/index.js +231 -18
- package/dist/index.min.css +1 -1
- package/dist/index.umd.js +231 -18
- package/dist/material-icon.d.ts +6 -0
- package/dist/sidenav.d.ts +29 -1
- package/package.json +1 -1
- package/sass/components/_sidenav.scss +194 -3
- package/sass/components/forms/_input-fields.scss +10 -10
package/dist/index.umd.js
CHANGED
|
@@ -967,6 +967,18 @@
|
|
|
967
967
|
'M16.59 8.59L12 13.17 7.41 8.59 6 10l6 6 6-6z', // chevron down
|
|
968
968
|
'M0 0h24v24H0z', // background
|
|
969
969
|
],
|
|
970
|
+
chevron_left: [
|
|
971
|
+
'M15.41 7.41L14 6l-6 6 6 6 1.41-1.41L10.83 12z', // chevron left
|
|
972
|
+
'M0 0h24v24H0z', // background
|
|
973
|
+
],
|
|
974
|
+
chevron_right: [
|
|
975
|
+
'M10 6L8.59 7.41 13.17 12l-4.58 4.59L10 18l6-6z', // chevron right
|
|
976
|
+
'M0 0h24v24H0z', // background
|
|
977
|
+
],
|
|
978
|
+
menu: [
|
|
979
|
+
'M3 18h18v-2H3v2zm0-5h18v-2H3v2zm0-7v2h18V6H3z', // hamburger menu
|
|
980
|
+
'M0 0h24v24H0z', // background
|
|
981
|
+
],
|
|
970
982
|
expand: [
|
|
971
983
|
'M19 13h-6v6h-2v-6H5v-2h6V5h2v6h6v2z', // plus
|
|
972
984
|
'M0 0h24v24H0z', // background
|
|
@@ -975,6 +987,18 @@
|
|
|
975
987
|
'M19 13H5v-2h14v2z', // minus
|
|
976
988
|
'M0 0h24v24H0z', // background
|
|
977
989
|
],
|
|
990
|
+
check: [
|
|
991
|
+
'M9 16.17L4.83 12l-1.42 1.41L9 19 21 7l-1.41-1.41z', // checkmark
|
|
992
|
+
'M0 0h24v24H0z', // background
|
|
993
|
+
],
|
|
994
|
+
radio_checked: [
|
|
995
|
+
'M12 7c-2.76 0-5 2.24-5 5s2.24 5 5 5 5-2.24 5-5-2.24-5-5-5zm0-5C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm0 18c-4.42 0-8-3.58-8-8s3.58-8 8-8 8 3.58 8 8-3.58 8-8 8z', // radio button checked
|
|
996
|
+
'M0 0h24v24H0z', // background
|
|
997
|
+
],
|
|
998
|
+
radio_unchecked: [
|
|
999
|
+
'M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm0 18c-4.42 0-8-3.58-8-8s3.58-8 8-8 8 3.58 8 8-3.58 8-8 8z', // radio button unchecked
|
|
1000
|
+
'M0 0h24v24H0z', // background
|
|
1001
|
+
],
|
|
978
1002
|
light_mode: [
|
|
979
1003
|
'M12 7c-2.76 0-5 2.24-5 5s2.24 5 5 5 5-2.24 5-5-2.24-5-5-5M2 13h2c.55 0 1-.45 1-1s-.45-1-1-1H2c-.55 0-1 .45-1 1s.45 1 1 1m18 0h2c.55 0 1-.45 1-1s-.45-1-1-1h-2c-.55 0-1 .45-1 1s.45 1 1 1M11 2v2c0 .55.45 1 1 1s1-.45 1-1V2c0-.55-.45-1-1-1s-1 .45-1 1m0 18v2c0 .55.45 1 1 1s1-.45 1-1v-2c0-.55-.45-1-1-1s-1 .45-1 1M5.99 4.58a.996.996 0 0 0-1.41 0 .996.996 0 0 0 0 1.41l1.06 1.06c.39.39 1.03.39 1.41 0s.39-1.03 0-1.41zm12.4 12.4a.996.996 0 0 0-1.41 0 .996.996 0 0 0 0 1.41l1.06 1.06c.39.39 1.03.39 1.41 0a.996.996 0 0 0 0-1.41zm1.06-11a.996.996 0 0 0 0-1.41.996.996 0 0 0-1.41 0l-1.06 1.06c-.39.39-.39 1.03 0 1.41s1.03.39 1.41 0zM7.05 18.4a.996.996 0 0 0 0-1.41.996.996 0 0 0-1.41 0l-1.06 1.06c-.39.39-.39 1.03 0 1.41s1.03.39 1.41 0z',
|
|
980
1004
|
'M0 0h24v24H0z', // background
|
|
@@ -3276,9 +3300,11 @@
|
|
|
3276
3300
|
? true
|
|
3277
3301
|
: false;
|
|
3278
3302
|
const rangeType = type === 'range' && !attrs.minmax;
|
|
3303
|
+
// Only add validate class if input is interactive and validation is needed
|
|
3304
|
+
const shouldValidate = !isNonInteractive && (validate || type === 'email' || type === 'url' || isNumeric);
|
|
3279
3305
|
return m('.input-field', { className: cn, style }, [
|
|
3280
3306
|
iconName ? m('i.material-icons.prefix', iconName) : undefined,
|
|
3281
|
-
m('input
|
|
3307
|
+
m('input', Object.assign(Object.assign({ class: shouldValidate ? 'validate' : undefined }, params), { type, tabindex: 0, id,
|
|
3282
3308
|
placeholder, value: controlled ? value : undefined, class: type === 'range' && attrs.vertical ? 'range-slider vertical' : undefined, style: type === 'range' && attrs.vertical
|
|
3283
3309
|
? {
|
|
3284
3310
|
height: attrs.height || '200px',
|
|
@@ -3359,6 +3385,17 @@
|
|
|
3359
3385
|
state.active = false;
|
|
3360
3386
|
const target = e.target;
|
|
3361
3387
|
state.hasInteracted = true;
|
|
3388
|
+
// Skip validation for readonly/disabled inputs
|
|
3389
|
+
if (attrs.readonly || attrs.disabled) {
|
|
3390
|
+
// Call original onblur if provided
|
|
3391
|
+
if (attrs.onblur) {
|
|
3392
|
+
attrs.onblur(e);
|
|
3393
|
+
}
|
|
3394
|
+
if (onchange && state.inputElement) {
|
|
3395
|
+
onchange(getValue(state.inputElement));
|
|
3396
|
+
}
|
|
3397
|
+
return;
|
|
3398
|
+
}
|
|
3362
3399
|
if (target && validate) {
|
|
3363
3400
|
const value = getValue(target);
|
|
3364
3401
|
// Only validate if user has entered some text
|
|
@@ -7801,12 +7838,27 @@
|
|
|
7801
7838
|
document.body.style.overflow = isOpen && mode === 'overlay' ? 'hidden' : '';
|
|
7802
7839
|
}
|
|
7803
7840
|
};
|
|
7841
|
+
const toggleExpanded = (attrs) => {
|
|
7842
|
+
const newExpandedState = !(attrs.isExpanded !== false);
|
|
7843
|
+
if (attrs.onExpandChange) {
|
|
7844
|
+
attrs.onExpandChange(newExpandedState);
|
|
7845
|
+
}
|
|
7846
|
+
};
|
|
7847
|
+
const toggleHamburger = (attrs) => {
|
|
7848
|
+
const newOpenState = !state.isOpen;
|
|
7849
|
+
if (attrs.onToggle) {
|
|
7850
|
+
attrs.onToggle(newOpenState);
|
|
7851
|
+
}
|
|
7852
|
+
};
|
|
7804
7853
|
return {
|
|
7805
7854
|
oninit: ({ attrs }) => {
|
|
7806
7855
|
state = {
|
|
7807
7856
|
id: attrs.id || uniqueId(),
|
|
7808
7857
|
isOpen: attrs.isOpen || false,
|
|
7809
7858
|
isAnimating: false,
|
|
7859
|
+
isExpanded: attrs.isExpanded !== false,
|
|
7860
|
+
activeItemIndex: null,
|
|
7861
|
+
selectedSubmenuItems: new Map(),
|
|
7810
7862
|
};
|
|
7811
7863
|
// Set up keyboard listener
|
|
7812
7864
|
if (typeof document !== 'undefined' && attrs.closeOnEscape !== false) {
|
|
@@ -7835,12 +7887,16 @@
|
|
|
7835
7887
|
}
|
|
7836
7888
|
},
|
|
7837
7889
|
view: ({ attrs, children }) => {
|
|
7838
|
-
const { position = 'left', mode = 'overlay', width = 300, className = '', showBackdrop = true, animationDuration = 300, fixed = false, } = attrs;
|
|
7890
|
+
const { position = 'left', mode = 'overlay', width = 300, className = '', showBackdrop = true, animationDuration = 300, fixed = false, showHamburger = false, expandable = false, } = attrs;
|
|
7839
7891
|
const isOpen = state.isOpen;
|
|
7892
|
+
const collapsedWidth = 60;
|
|
7893
|
+
const isExpanded = attrs.isExpanded !== false;
|
|
7894
|
+
const currentWidth = expandable && !isExpanded ? collapsedWidth : width;
|
|
7840
7895
|
return [
|
|
7841
|
-
// Backdrop (using existing materialize class)
|
|
7896
|
+
// Backdrop (using existing materialize class) - only for overlay mode
|
|
7842
7897
|
showBackdrop &&
|
|
7843
7898
|
mode === 'overlay' &&
|
|
7899
|
+
!fixed &&
|
|
7844
7900
|
m('.sidenav-overlay', {
|
|
7845
7901
|
style: {
|
|
7846
7902
|
display: isOpen ? 'block' : 'none',
|
|
@@ -7851,49 +7907,206 @@
|
|
|
7851
7907
|
// Sidenav (using existing materialize structure)
|
|
7852
7908
|
m('ul.sidenav', {
|
|
7853
7909
|
id: state.id,
|
|
7854
|
-
class: [
|
|
7910
|
+
class: [
|
|
7911
|
+
position === 'right' ? 'right-aligned' : '',
|
|
7912
|
+
fixed ? 'sidenav-fixed' : '',
|
|
7913
|
+
expandable && !isExpanded ? 'sidenav-collapsed' : '',
|
|
7914
|
+
className,
|
|
7915
|
+
]
|
|
7855
7916
|
.filter(Boolean)
|
|
7856
7917
|
.join(' ') || undefined,
|
|
7857
7918
|
style: {
|
|
7858
|
-
width: `${
|
|
7919
|
+
width: `${currentWidth}px`,
|
|
7859
7920
|
transform: isOpen ? 'translateX(0)' : position === 'left' ? 'translateX(-105%)' : 'translateX(105%)',
|
|
7860
7921
|
'transition-duration': `${animationDuration}ms`,
|
|
7922
|
+
'transition-property': 'transform, width',
|
|
7861
7923
|
},
|
|
7862
|
-
},
|
|
7924
|
+
}, [
|
|
7925
|
+
// Hamburger toggle button (inside sidenav, at the top)
|
|
7926
|
+
showHamburger &&
|
|
7927
|
+
m('li.sidenav-hamburger-item', {
|
|
7928
|
+
style: {
|
|
7929
|
+
display: 'flex',
|
|
7930
|
+
'justify-content': position === 'right' ? 'flex-end' : 'flex-start',
|
|
7931
|
+
'align-items': 'center',
|
|
7932
|
+
padding: '12px 16px',
|
|
7933
|
+
cursor: 'pointer',
|
|
7934
|
+
'border-bottom': '1px solid rgba(0,0,0,0.1)',
|
|
7935
|
+
},
|
|
7936
|
+
onclick: () => toggleHamburger(attrs),
|
|
7937
|
+
}, m(MaterialIcon, {
|
|
7938
|
+
name: 'menu',
|
|
7939
|
+
style: { width: '24px', height: '24px' },
|
|
7940
|
+
})),
|
|
7941
|
+
// Expand/collapse toggle button (if expandable, right below hamburger)
|
|
7942
|
+
expandable &&
|
|
7943
|
+
m('li.sidenav-expand-toggle', {
|
|
7944
|
+
style: {
|
|
7945
|
+
display: 'flex',
|
|
7946
|
+
'justify-content': position === 'right' ? 'flex-end' : 'flex-start',
|
|
7947
|
+
'align-items': 'center',
|
|
7948
|
+
padding: '12px 16px',
|
|
7949
|
+
cursor: 'pointer',
|
|
7950
|
+
'border-bottom': '1px solid rgba(0,0,0,0.1)',
|
|
7951
|
+
},
|
|
7952
|
+
onclick: () => toggleExpanded(attrs),
|
|
7953
|
+
}, m(MaterialIcon, {
|
|
7954
|
+
name: position === 'right'
|
|
7955
|
+
? (isExpanded ? 'chevron_right' : 'chevron_left')
|
|
7956
|
+
: (isExpanded ? 'chevron_left' : 'chevron_right'),
|
|
7957
|
+
style: { width: '24px', height: '24px' },
|
|
7958
|
+
})),
|
|
7959
|
+
// Children (menu items) - inject internal props
|
|
7960
|
+
Array.isArray(children)
|
|
7961
|
+
? children.map((child) => {
|
|
7962
|
+
if (child && typeof child === 'object' && 'tag' in child) {
|
|
7963
|
+
// Clone the vnode and add internal props
|
|
7964
|
+
return Object.assign(Object.assign({}, child), { attrs: Object.assign(Object.assign({}, child.attrs), { _isExpanded: isExpanded, _position: position }) });
|
|
7965
|
+
}
|
|
7966
|
+
return child;
|
|
7967
|
+
})
|
|
7968
|
+
: children,
|
|
7969
|
+
]),
|
|
7863
7970
|
];
|
|
7864
7971
|
},
|
|
7865
7972
|
};
|
|
7866
7973
|
};
|
|
7974
|
+
/**
|
|
7975
|
+
* Sidenav Submenu Item Component
|
|
7976
|
+
*/
|
|
7977
|
+
const NavbarSubItem = () => {
|
|
7978
|
+
return {
|
|
7979
|
+
view: ({ attrs }) => {
|
|
7980
|
+
const { text, icon, selected = false, value, onSelect, mode, isExpanded, position = 'left' } = attrs;
|
|
7981
|
+
const handleClick = () => {
|
|
7982
|
+
if (onSelect) {
|
|
7983
|
+
onSelect(value !== undefined ? value : text, !selected);
|
|
7984
|
+
}
|
|
7985
|
+
};
|
|
7986
|
+
const isRightAligned = position === 'right';
|
|
7987
|
+
const submenuContent = isRightAligned
|
|
7988
|
+
? [
|
|
7989
|
+
// Right-aligned: text on left, icons on right
|
|
7990
|
+
isExpanded && m('span', { style: { 'flex': '1', 'text-align': 'left' } }, text),
|
|
7991
|
+
icon && isExpanded && m('i.material-icons', { style: { 'font-size': '18px' } }, icon),
|
|
7992
|
+
m(MaterialIcon, {
|
|
7993
|
+
name: mode === 'checkbox' ? (selected ? 'check' : 'close') : selected ? 'radio_checked' : 'radio_unchecked',
|
|
7994
|
+
style: {
|
|
7995
|
+
width: '18px',
|
|
7996
|
+
height: '18px',
|
|
7997
|
+
opacity: mode === 'checkbox' && !selected ? '0.3' : '1',
|
|
7998
|
+
},
|
|
7999
|
+
}),
|
|
8000
|
+
]
|
|
8001
|
+
: [
|
|
8002
|
+
// Left-aligned: indicator on left, text and icon on right
|
|
8003
|
+
m(MaterialIcon, {
|
|
8004
|
+
name: mode === 'checkbox' ? (selected ? 'check' : 'close') : selected ? 'radio_checked' : 'radio_unchecked',
|
|
8005
|
+
style: {
|
|
8006
|
+
width: '18px',
|
|
8007
|
+
height: '18px',
|
|
8008
|
+
opacity: mode === 'checkbox' && !selected ? '0.3' : '1',
|
|
8009
|
+
},
|
|
8010
|
+
}),
|
|
8011
|
+
icon && isExpanded && m('i.material-icons', { style: { 'font-size': '18px', 'margin-left': '8px' } }, icon),
|
|
8012
|
+
isExpanded && m('span', { style: { 'margin-left': icon ? '8px' : '8px' } }, text),
|
|
8013
|
+
];
|
|
8014
|
+
return m('li.sidenav-subitem', {
|
|
8015
|
+
class: selected ? 'selected' : '',
|
|
8016
|
+
style: {
|
|
8017
|
+
padding: isExpanded ? '8px 16px 8px 48px' : '8px 16px',
|
|
8018
|
+
cursor: 'pointer',
|
|
8019
|
+
display: 'flex',
|
|
8020
|
+
'align-items': 'center',
|
|
8021
|
+
gap: '8px',
|
|
8022
|
+
'font-size': '0.9em',
|
|
8023
|
+
'justify-content': isRightAligned ? 'space-between' : 'flex-start',
|
|
8024
|
+
},
|
|
8025
|
+
onclick: handleClick,
|
|
8026
|
+
}, submenuContent);
|
|
8027
|
+
},
|
|
8028
|
+
};
|
|
8029
|
+
};
|
|
7867
8030
|
/**
|
|
7868
8031
|
* Sidenav Item Component
|
|
7869
8032
|
* Individual items for the sidenav menu
|
|
7870
8033
|
*/
|
|
7871
8034
|
const SidenavItem = () => {
|
|
8035
|
+
let isSubmenuOpen = false;
|
|
7872
8036
|
return {
|
|
7873
8037
|
view: ({ attrs, children }) => {
|
|
7874
|
-
const { text, icon, active = false, disabled = false, onclick, href, className = '', divider = false, subheader = false, } = attrs;
|
|
8038
|
+
const { text, icon, active = false, disabled = false, onclick, href, className = '', divider = false, subheader = false, submenu = [], submenuMode = 'checkbox', } = attrs;
|
|
7875
8039
|
if (divider) {
|
|
7876
8040
|
return m('li.divider');
|
|
7877
8041
|
}
|
|
7878
8042
|
if (subheader) {
|
|
7879
8043
|
return m('li.subheader', text || children);
|
|
7880
8044
|
}
|
|
7881
|
-
const
|
|
7882
|
-
const
|
|
7883
|
-
|
|
7884
|
-
|
|
8045
|
+
const hasSubmenu = submenu && submenu.length > 0;
|
|
8046
|
+
const itemClasses = [
|
|
8047
|
+
active ? 'active' : '',
|
|
8048
|
+
disabled ? 'disabled' : '',
|
|
8049
|
+
hasSubmenu ? 'has-submenu' : '',
|
|
8050
|
+
className,
|
|
8051
|
+
]
|
|
8052
|
+
.filter(Boolean)
|
|
8053
|
+
.join(' ') || undefined;
|
|
8054
|
+
const handleMainClick = (e) => {
|
|
8055
|
+
e.preventDefault();
|
|
8056
|
+
if (hasSubmenu) {
|
|
8057
|
+
isSubmenuOpen = active ? !isSubmenuOpen : true;
|
|
8058
|
+
}
|
|
8059
|
+
if (onclick && !disabled) {
|
|
8060
|
+
onclick(e);
|
|
8061
|
+
}
|
|
8062
|
+
};
|
|
8063
|
+
// Get internal props passed from parent Sidenav
|
|
8064
|
+
const isExpanded = attrs._isExpanded !== false;
|
|
8065
|
+
const position = attrs._position || 'left';
|
|
8066
|
+
const isRightAligned = position === 'right';
|
|
8067
|
+
// In expanded mode, icons are at the outside edge
|
|
8068
|
+
// In collapsed mode, icons are centered
|
|
8069
|
+
const content = isRightAligned
|
|
8070
|
+
? [
|
|
8071
|
+
// Right-aligned: text on left, icon on right
|
|
8072
|
+
isExpanded && m('span.sidenav-item-text', { style: { 'flex': '1', 'text-align': 'left', 'margin-right': '8px' } }, text || children),
|
|
8073
|
+
m('i.material-icons', { style: { 'min-width': '24px', 'width': '24px' } }, icon || ''),
|
|
8074
|
+
]
|
|
8075
|
+
: [
|
|
8076
|
+
// Left-aligned: icon on left, text on right
|
|
8077
|
+
m('i.material-icons', { style: { 'min-width': '24px', 'width': '24px' } }, icon || ''),
|
|
8078
|
+
isExpanded && m('span.sidenav-item-text', { style: { 'margin-left': '8px', 'flex': '1' } }, text || children),
|
|
8079
|
+
];
|
|
8080
|
+
const linkStyle = {
|
|
8081
|
+
display: 'flex',
|
|
8082
|
+
'align-items': 'center',
|
|
8083
|
+
padding: isExpanded ? '12px 16px' : '12px 18px',
|
|
8084
|
+
'justify-content': isExpanded ? (isRightAligned ? 'flex-end' : 'flex-start') : 'center',
|
|
8085
|
+
};
|
|
8086
|
+
const mainItem = href && !disabled
|
|
8087
|
+
? m('li', { class: itemClasses }, [
|
|
7885
8088
|
m('a', {
|
|
7886
8089
|
href,
|
|
7887
|
-
onclick:
|
|
8090
|
+
onclick: handleMainClick,
|
|
8091
|
+
style: linkStyle,
|
|
8092
|
+
}, content),
|
|
8093
|
+
])
|
|
8094
|
+
: m('li', { class: itemClasses }, [
|
|
8095
|
+
m('a', {
|
|
8096
|
+
onclick: handleMainClick,
|
|
8097
|
+
href: '#!',
|
|
8098
|
+
style: linkStyle,
|
|
7888
8099
|
}, content),
|
|
7889
8100
|
]);
|
|
8101
|
+
// Return main item with submenu if applicable
|
|
8102
|
+
if (hasSubmenu && active && isSubmenuOpen) {
|
|
8103
|
+
return [
|
|
8104
|
+
mainItem,
|
|
8105
|
+
submenu.map((subItem) => m(NavbarSubItem, Object.assign(Object.assign({}, subItem), { mode: submenuMode, isExpanded,
|
|
8106
|
+
position }))),
|
|
8107
|
+
];
|
|
7890
8108
|
}
|
|
7891
|
-
return
|
|
7892
|
-
m('a', {
|
|
7893
|
-
onclick: disabled ? undefined : onclick,
|
|
7894
|
-
href: '#!',
|
|
7895
|
-
}, content),
|
|
7896
|
-
]);
|
|
8109
|
+
return mainItem;
|
|
7897
8110
|
},
|
|
7898
8111
|
};
|
|
7899
8112
|
};
|
package/dist/material-icon.d.ts
CHANGED
|
@@ -3,8 +3,14 @@ declare const iconPaths: {
|
|
|
3
3
|
readonly caret: readonly ["M7 10l5 5 5-5z", "M0 0h24v24H0z"];
|
|
4
4
|
readonly close: readonly ["M18.3 5.71a1 1 0 0 0-1.41 0L12 10.59 7.11 5.7A1 1 0 0 0 5.7 7.11L10.59 12l-4.89 4.89a1 1 0 1 0 1.41 1.41L12 13.41l4.89 4.89a1 1 0 0 0 1.41-1.41L13.41 12l4.89-4.89a1 1 0 0 0 0-1.4z", "M0 0h24v24H0z"];
|
|
5
5
|
readonly chevron: readonly ["M16.59 8.59L12 13.17 7.41 8.59 6 10l6 6 6-6z", "M0 0h24v24H0z"];
|
|
6
|
+
readonly chevron_left: readonly ["M15.41 7.41L14 6l-6 6 6 6 1.41-1.41L10.83 12z", "M0 0h24v24H0z"];
|
|
7
|
+
readonly chevron_right: readonly ["M10 6L8.59 7.41 13.17 12l-4.58 4.59L10 18l6-6z", "M0 0h24v24H0z"];
|
|
8
|
+
readonly menu: readonly ["M3 18h18v-2H3v2zm0-5h18v-2H3v2zm0-7v2h18V6H3z", "M0 0h24v24H0z"];
|
|
6
9
|
readonly expand: readonly ["M19 13h-6v6h-2v-6H5v-2h6V5h2v6h6v2z", "M0 0h24v24H0z"];
|
|
7
10
|
readonly collapse: readonly ["M19 13H5v-2h14v2z", "M0 0h24v24H0z"];
|
|
11
|
+
readonly check: readonly ["M9 16.17L4.83 12l-1.42 1.41L9 19 21 7l-1.41-1.41z", "M0 0h24v24H0z"];
|
|
12
|
+
readonly radio_checked: readonly ["M12 7c-2.76 0-5 2.24-5 5s2.24 5 5 5 5-2.24 5-5-2.24-5-5-5zm0-5C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm0 18c-4.42 0-8-3.58-8-8s3.58-8 8-8 8 3.58 8 8-3.58 8-8 8z", "M0 0h24v24H0z"];
|
|
13
|
+
readonly radio_unchecked: readonly ["M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm0 18c-4.42 0-8-3.58-8-8s3.58-8 8-8 8 3.58 8 8-3.58 8-8 8z", "M0 0h24v24H0z"];
|
|
8
14
|
readonly light_mode: readonly ["M12 7c-2.76 0-5 2.24-5 5s2.24 5 5 5 5-2.24 5-5-2.24-5-5-5M2 13h2c.55 0 1-.45 1-1s-.45-1-1-1H2c-.55 0-1 .45-1 1s.45 1 1 1m18 0h2c.55 0 1-.45 1-1s-.45-1-1-1h-2c-.55 0-1 .45-1 1s.45 1 1 1M11 2v2c0 .55.45 1 1 1s1-.45 1-1V2c0-.55-.45-1-1-1s-1 .45-1 1m0 18v2c0 .55.45 1 1 1s1-.45 1-1v-2c0-.55-.45-1-1-1s-1 .45-1 1M5.99 4.58a.996.996 0 0 0-1.41 0 .996.996 0 0 0 0 1.41l1.06 1.06c.39.39 1.03.39 1.41 0s.39-1.03 0-1.41zm12.4 12.4a.996.996 0 0 0-1.41 0 .996.996 0 0 0 0 1.41l1.06 1.06c.39.39 1.03.39 1.41 0a.996.996 0 0 0 0-1.41zm1.06-11a.996.996 0 0 0 0-1.41.996.996 0 0 0-1.41 0l-1.06 1.06c-.39.39-.39 1.03 0 1.41s1.03.39 1.41 0zM7.05 18.4a.996.996 0 0 0 0-1.41.996.996 0 0 0-1.41 0l-1.06 1.06c-.39.39-.39 1.03 0 1.41s1.03.39 1.41 0z", "M0 0h24v24H0z"];
|
|
9
15
|
readonly dark_mode: readonly ["M12 3a9 9 0 1 0 9 9c0-.46-.04-.92-.1-1.36a5.39 5.39 0 0 1-4.4 2.26 5.4 5.4 0 0 1-3.14-9.8c-.44-.06-.9-.1-1.36-.1z", "M0 0h24v24H0z"];
|
|
10
16
|
};
|
package/dist/sidenav.d.ts
CHANGED
|
@@ -1,4 +1,16 @@
|
|
|
1
1
|
import { FactoryComponent, Attributes } from 'mithril';
|
|
2
|
+
export interface NavbarSubItemAttrs {
|
|
3
|
+
/** Text content of the submenu item */
|
|
4
|
+
text: string;
|
|
5
|
+
/** Optional icon name */
|
|
6
|
+
icon?: string;
|
|
7
|
+
/** Whether this submenu item is selected */
|
|
8
|
+
selected?: boolean;
|
|
9
|
+
/** Value for the submenu item */
|
|
10
|
+
value?: any;
|
|
11
|
+
/** Selection callback */
|
|
12
|
+
onSelect?: (value: any, selected: boolean) => void;
|
|
13
|
+
}
|
|
2
14
|
export interface SidenavAttrs extends Attributes {
|
|
3
15
|
/** Unique ID for the sidenav */
|
|
4
16
|
id?: string;
|
|
@@ -10,7 +22,7 @@ export interface SidenavAttrs extends Attributes {
|
|
|
10
22
|
position?: 'left' | 'right';
|
|
11
23
|
/** Whether sidenav should overlay content or push it */
|
|
12
24
|
mode?: 'overlay' | 'push';
|
|
13
|
-
/** Width of the sidenav in pixels */
|
|
25
|
+
/** Width of the sidenav in pixels (when expanded) */
|
|
14
26
|
width?: number;
|
|
15
27
|
/** Custom class for the sidenav */
|
|
16
28
|
className?: string;
|
|
@@ -26,6 +38,14 @@ export interface SidenavAttrs extends Attributes {
|
|
|
26
38
|
fixed?: boolean;
|
|
27
39
|
/** Breakpoint for responsive behavior (in pixels) */
|
|
28
40
|
breakpoint?: number;
|
|
41
|
+
/** Show hamburger toggle button */
|
|
42
|
+
showHamburger?: boolean;
|
|
43
|
+
/** Enable collapse/expand functionality */
|
|
44
|
+
expandable?: boolean;
|
|
45
|
+
/** Whether the sidenav is expanded (shows icons + text) */
|
|
46
|
+
isExpanded?: boolean;
|
|
47
|
+
/** Callback when expand state changes */
|
|
48
|
+
onExpandChange?: (expanded: boolean) => void;
|
|
29
49
|
}
|
|
30
50
|
export interface SidenavItemAttrs {
|
|
31
51
|
/** Text content of the item */
|
|
@@ -46,6 +66,14 @@ export interface SidenavItemAttrs {
|
|
|
46
66
|
divider?: boolean;
|
|
47
67
|
/** Whether this is a subheader */
|
|
48
68
|
subheader?: boolean;
|
|
69
|
+
/** Submenu items */
|
|
70
|
+
submenu?: NavbarSubItemAttrs[];
|
|
71
|
+
/** Submenu selection mode */
|
|
72
|
+
submenuMode?: 'checkbox' | 'radio';
|
|
73
|
+
/** @internal - Whether the sidenav is expanded (passed from parent) */
|
|
74
|
+
_isExpanded?: boolean;
|
|
75
|
+
/** @internal - Position of the sidenav (passed from parent) */
|
|
76
|
+
_position?: 'left' | 'right';
|
|
49
77
|
}
|
|
50
78
|
/**
|
|
51
79
|
* Sidenav Component
|
package/package.json
CHANGED
|
@@ -109,7 +109,9 @@
|
|
|
109
109
|
}
|
|
110
110
|
|
|
111
111
|
// Legacy Sidenav Styles (maintain backward compatibility)
|
|
112
|
-
|
|
112
|
+
ul.sidenav.right-aligned li > a:not(.btn):not(.btn-large):not(.btn-flat):not(.btn-floating) i.material-icons {
|
|
113
|
+
margin: 0;
|
|
114
|
+
}
|
|
113
115
|
.sidenav {
|
|
114
116
|
position: fixed;
|
|
115
117
|
width: variables.$sidenav-width;
|
|
@@ -191,7 +193,8 @@
|
|
|
191
193
|
li > a:not(.btn):not(.btn-large):not(.btn-flat):not(.btn-floating) {
|
|
192
194
|
&:hover { background-color: var(--mm-border-color, rgba(0,0,0,.05));}
|
|
193
195
|
|
|
194
|
-
color: var(--mm-text-primary, variables.$sidenav-font-color);
|
|
196
|
+
// color: var(--mm-text-primary, variables.$sidenav-font-color);
|
|
197
|
+
color: var(--mm-nav-active-text, #fff);
|
|
195
198
|
display: block;
|
|
196
199
|
font-size: variables.$sidenav-font-size;
|
|
197
200
|
font-weight: 500;
|
|
@@ -208,6 +211,7 @@
|
|
|
208
211
|
margin: 0 (variables.$sidenav-padding * 2) 0 0;
|
|
209
212
|
width: math.div(variables.$sidenav-item-height, 2);
|
|
210
213
|
color: var(--mm-text-secondary, rgba(0,0,0,.54));
|
|
214
|
+
user-select: none;
|
|
211
215
|
}
|
|
212
216
|
}
|
|
213
217
|
|
|
@@ -341,7 +345,7 @@
|
|
|
341
345
|
.sidenav.sidenav-fixed .collapsible-body > ul:not(.collapsible) > li.active {
|
|
342
346
|
background-color: variables.$primary-color;
|
|
343
347
|
a {
|
|
344
|
-
color:
|
|
348
|
+
color: var(--mm-nav-active-text, #fff);
|
|
345
349
|
}
|
|
346
350
|
}
|
|
347
351
|
.sidenav .collapsible-body {
|
|
@@ -368,3 +372,190 @@
|
|
|
368
372
|
.sidenav-overlay {
|
|
369
373
|
pointer-events: auto;
|
|
370
374
|
}
|
|
375
|
+
|
|
376
|
+
// Hamburger button styles (legacy - external button)
|
|
377
|
+
.sidenav-hamburger {
|
|
378
|
+
background: var(--mm-surface-color, #fff);
|
|
379
|
+
border-radius: 4px;
|
|
380
|
+
box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
|
|
381
|
+
transition: background-color 0.2s ease, box-shadow 0.2s ease;
|
|
382
|
+
|
|
383
|
+
&:hover {
|
|
384
|
+
background: var(--mm-border-color, rgba(0, 0, 0, 0.05));
|
|
385
|
+
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15);
|
|
386
|
+
}
|
|
387
|
+
|
|
388
|
+
svg {
|
|
389
|
+
fill: var(--mm-text-primary, rgba(0, 0, 0, 0.87));
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
|
|
393
|
+
// Hamburger item inside sidenav
|
|
394
|
+
.sidenav-hamburger-item {
|
|
395
|
+
list-style: none;
|
|
396
|
+
|
|
397
|
+
&:hover {
|
|
398
|
+
background: var(--mm-border-color, rgba(0, 0, 0, 0.05));
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
svg {
|
|
402
|
+
fill: var(--mm-text-secondary, rgba(0, 0, 0, 0.6));
|
|
403
|
+
}
|
|
404
|
+
}
|
|
405
|
+
|
|
406
|
+
// Collapsed sidenav state
|
|
407
|
+
.sidenav.sidenav-collapsed {
|
|
408
|
+
width: 60px !important;
|
|
409
|
+
|
|
410
|
+
.sidenav-item-text {
|
|
411
|
+
display: none;
|
|
412
|
+
}
|
|
413
|
+
|
|
414
|
+
li > a:not(.btn):not(.btn-large):not(.btn-flat):not(.btn-floating) {
|
|
415
|
+
padding: 0 18px;
|
|
416
|
+
justify-content: center;
|
|
417
|
+
|
|
418
|
+
& > i,
|
|
419
|
+
& > i.material-icons {
|
|
420
|
+
margin: 0;
|
|
421
|
+
float: none;
|
|
422
|
+
}
|
|
423
|
+
}
|
|
424
|
+
|
|
425
|
+
.subheader {
|
|
426
|
+
display: none;
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
.sidenav-subitem {
|
|
430
|
+
padding: 8px 16px !important;
|
|
431
|
+
justify-content: center;
|
|
432
|
+
|
|
433
|
+
span {
|
|
434
|
+
display: none;
|
|
435
|
+
}
|
|
436
|
+
}
|
|
437
|
+
}
|
|
438
|
+
|
|
439
|
+
// Expand/collapse toggle button
|
|
440
|
+
.sidenav-expand-toggle {
|
|
441
|
+
&:hover {
|
|
442
|
+
background: var(--mm-border-color, rgba(0, 0, 0, 0.05));
|
|
443
|
+
}
|
|
444
|
+
|
|
445
|
+
svg {
|
|
446
|
+
fill: var(--mm-text-secondary, rgba(0, 0, 0, 0.6));
|
|
447
|
+
transition: transform 0.2s ease;
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
|
|
451
|
+
// Submenu item styles
|
|
452
|
+
.sidenav-subitem {
|
|
453
|
+
list-style: none;
|
|
454
|
+
transition: background-color 0.2s ease;
|
|
455
|
+
|
|
456
|
+
&:hover {
|
|
457
|
+
background: var(--mm-border-color, rgba(0, 0, 0, 0.05));
|
|
458
|
+
}
|
|
459
|
+
|
|
460
|
+
// Don't show selected background - only the check/radio icon indicates selection
|
|
461
|
+
// to avoid confusion with multiple active menu items
|
|
462
|
+
&.selected {
|
|
463
|
+
svg {
|
|
464
|
+
fill: var(--mm-primary-color, #26a69a);
|
|
465
|
+
}
|
|
466
|
+
}
|
|
467
|
+
|
|
468
|
+
svg {
|
|
469
|
+
fill: var(--mm-text-secondary, rgba(0, 0, 0, 0.6));
|
|
470
|
+
transition: fill 0.2s ease;
|
|
471
|
+
}
|
|
472
|
+
|
|
473
|
+
i.material-icons {
|
|
474
|
+
color: var(--mm-text-secondary, rgba(0, 0, 0, 0.6));
|
|
475
|
+
}
|
|
476
|
+
}
|
|
477
|
+
|
|
478
|
+
// Menu item with submenu indicator
|
|
479
|
+
.sidenav li.has-submenu {
|
|
480
|
+
&.active > a {
|
|
481
|
+
background: var(--mm-primary-color-light, rgba(38, 166, 154, 0.1));
|
|
482
|
+
color: var(--mm-primary-color, #26a69a);
|
|
483
|
+
}
|
|
484
|
+
}
|
|
485
|
+
|
|
486
|
+
// Dark theme support
|
|
487
|
+
[data-theme="dark"] {
|
|
488
|
+
.sidenav-hamburger {
|
|
489
|
+
background: var(--mm-surface-color, #1e1e1e);
|
|
490
|
+
|
|
491
|
+
svg {
|
|
492
|
+
fill: var(--mm-text-primary, rgba(255, 255, 255, 0.87));
|
|
493
|
+
}
|
|
494
|
+
}
|
|
495
|
+
|
|
496
|
+
.sidenav {
|
|
497
|
+
background-color: var(--mm-surface-color, #1e1e1e);
|
|
498
|
+
|
|
499
|
+
li > a:not(.btn):not(.btn-large):not(.btn-flat):not(.btn-floating) {
|
|
500
|
+
color: var(--mm-text-primary, rgba(255, 255, 255, 0.87));
|
|
501
|
+
|
|
502
|
+
&:hover {
|
|
503
|
+
background-color: var(--mm-border-color, rgba(255, 255, 255, 0.05));
|
|
504
|
+
}
|
|
505
|
+
|
|
506
|
+
& > i,
|
|
507
|
+
& > i.material-icons {
|
|
508
|
+
color: var(--mm-text-secondary, rgba(255, 255, 255, 0.6));
|
|
509
|
+
}
|
|
510
|
+
}
|
|
511
|
+
|
|
512
|
+
li.active {
|
|
513
|
+
background-color: rgba(255, 255, 255, 0.05);
|
|
514
|
+
|
|
515
|
+
& > a:not(.btn):not(.btn-large):not(.btn-flat):not(.btn-floating) {
|
|
516
|
+
color: var(--mm-nav-active-text, #fff);
|
|
517
|
+
|
|
518
|
+
& > i,
|
|
519
|
+
& > i.material-icons {
|
|
520
|
+
color: var(--mm-nav-active-text, #fff);
|
|
521
|
+
}
|
|
522
|
+
}
|
|
523
|
+
}
|
|
524
|
+
|
|
525
|
+
.collapsible-body > ul:not(.collapsible) > li.active a {
|
|
526
|
+
color: var(--mm-nav-active-text, #fff);
|
|
527
|
+
|
|
528
|
+
i,
|
|
529
|
+
i.material-icons {
|
|
530
|
+
color: var(--mm-nav-active-text, #fff);
|
|
531
|
+
}
|
|
532
|
+
}
|
|
533
|
+
|
|
534
|
+
.subheader {
|
|
535
|
+
color: var(--mm-text-secondary, rgba(255, 255, 255, 0.6));
|
|
536
|
+
}
|
|
537
|
+
}
|
|
538
|
+
|
|
539
|
+
.sidenav-expand-toggle svg {
|
|
540
|
+
fill: var(--mm-text-secondary, rgba(255, 255, 255, 0.6));
|
|
541
|
+
}
|
|
542
|
+
|
|
543
|
+
.sidenav-subitem {
|
|
544
|
+
&:hover {
|
|
545
|
+
background: var(--mm-border-color, rgba(255, 255, 255, 0.05));
|
|
546
|
+
}
|
|
547
|
+
|
|
548
|
+
svg {
|
|
549
|
+
fill: var(--mm-text-secondary, rgba(255, 255, 255, 0.6));
|
|
550
|
+
}
|
|
551
|
+
|
|
552
|
+
i.material-icons {
|
|
553
|
+
color: var(--mm-text-secondary, rgba(255, 255, 255, 0.6));
|
|
554
|
+
}
|
|
555
|
+
}
|
|
556
|
+
}
|
|
557
|
+
|
|
558
|
+
// Animation for smooth width transitions
|
|
559
|
+
.sidenav {
|
|
560
|
+
transition: transform 0.3s ease, width 0.3s ease;
|
|
561
|
+
}
|