@ndla/ui 19.2.0 → 20.0.3

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.
Files changed (75) hide show
  1. package/README.md +1 -1
  2. package/es/LearningPaths/LearningPathMenu.js +8 -5
  3. package/es/LearningPaths/LearningPathMenuIntro.js +19 -8
  4. package/es/Masthead/Masthead.js +1 -0
  5. package/es/Messages/MessageBanner.js +3 -3
  6. package/es/MyNdla/Resource/FolderInput.js +29 -36
  7. package/es/NDLAFilm/FilmSlideshow.js +8 -8
  8. package/es/Resource/ListResource.js +6 -6
  9. package/es/Search/LoadingWrapper.js +2 -2
  10. package/es/Search/SearchResult.js +1 -1
  11. package/es/SearchTypeResult/SearchTypeResult.js +3 -3
  12. package/es/TopicMenu/TopicMenu.js +14 -1
  13. package/es/TreeStructure/FolderNameInput.js +5 -5
  14. package/es/all.css +1 -1
  15. package/es/index.js +0 -1
  16. package/es/locale/messages-en.js +10 -2
  17. package/es/locale/messages-nb.js +10 -2
  18. package/es/locale/messages-nn.js +10 -2
  19. package/es/locale/messages-se.js +10 -2
  20. package/es/locale/messages-sma.js +10 -2
  21. package/lib/LearningPaths/LearningPathMenu.d.ts +2 -1
  22. package/lib/LearningPaths/LearningPathMenu.js +8 -5
  23. package/lib/LearningPaths/LearningPathMenuIntro.d.ts +3 -1
  24. package/lib/LearningPaths/LearningPathMenuIntro.js +19 -8
  25. package/lib/Masthead/Masthead.js +1 -0
  26. package/lib/Messages/MessageBanner.js +3 -3
  27. package/lib/MyNdla/Resource/FolderInput.d.ts +2 -2
  28. package/lib/MyNdla/Resource/FolderInput.js +26 -33
  29. package/lib/NDLAFilm/FilmSlideshow.js +10 -10
  30. package/lib/Resource/ListResource.js +6 -6
  31. package/lib/Search/LoadingWrapper.js +3 -3
  32. package/lib/Search/SearchResult.js +2 -2
  33. package/lib/SearchTypeResult/SearchTypeResult.js +4 -4
  34. package/lib/TopicMenu/TopicMenu.js +14 -1
  35. package/lib/TreeStructure/FolderNameInput.js +6 -6
  36. package/lib/all.css +1 -1
  37. package/lib/index.d.ts +0 -1
  38. package/lib/index.js +0 -9
  39. package/lib/locale/messages-en.d.ts +9 -1
  40. package/lib/locale/messages-en.js +10 -2
  41. package/lib/locale/messages-nb.d.ts +9 -1
  42. package/lib/locale/messages-nb.js +10 -2
  43. package/lib/locale/messages-nn.d.ts +9 -1
  44. package/lib/locale/messages-nn.js +10 -2
  45. package/lib/locale/messages-se.d.ts +9 -1
  46. package/lib/locale/messages-se.js +10 -2
  47. package/lib/locale/messages-sma.d.ts +9 -1
  48. package/lib/locale/messages-sma.js +10 -2
  49. package/package.json +14 -13
  50. package/src/LearningPaths/LearningPathMenu.tsx +9 -1
  51. package/src/LearningPaths/LearningPathMenuIntro.tsx +15 -2
  52. package/src/Masthead/Masthead.tsx +4 -1
  53. package/src/Messages/MessageBanner.tsx +1 -1
  54. package/src/MyNdla/Resource/FolderInput.tsx +41 -44
  55. package/src/NDLAFilm/FilmSlideshow.tsx +1 -1
  56. package/src/Resource/ListResource.tsx +1 -0
  57. package/src/Search/LoadingWrapper.tsx +1 -1
  58. package/src/Search/SearchResult.jsx +1 -1
  59. package/src/SearchTypeResult/SearchTypeResult.tsx +1 -1
  60. package/src/TopicMenu/TopicMenu.jsx +15 -2
  61. package/src/TreeStructure/FolderNameInput.tsx +1 -1
  62. package/src/index.ts +0 -2
  63. package/src/locale/messages-en.ts +9 -1
  64. package/src/locale/messages-nb.ts +10 -1
  65. package/src/locale/messages-nn.ts +9 -1
  66. package/src/locale/messages-se.ts +10 -1
  67. package/src/locale/messages-sma.ts +10 -1
  68. package/es/Spinner/Spinner.js +0 -42
  69. package/es/Spinner/index.js +0 -2
  70. package/lib/Spinner/Spinner.d.ts +0 -16
  71. package/lib/Spinner/Spinner.js +0 -54
  72. package/lib/Spinner/index.d.ts +0 -2
  73. package/lib/Spinner/index.js +0 -13
  74. package/src/Spinner/Spinner.tsx +0 -46
  75. package/src/Spinner/index.ts +0 -3
package/lib/index.d.ts CHANGED
@@ -34,7 +34,6 @@ export type { FigureType } from './Figure';
34
34
  export { LanguageSelector } from './LanguageSelector';
35
35
  export { LearningPathWrapper, LearningPathContent, LearningPathMenu, LearningPathSticky, LearningPathInformation, LearningPathStickySibling, LearningPathStickyPlaceholder, LearningPathLastStepNavigation, LearningPathMobileStepInfo, LearningPathMobileHeader, } from './LearningPaths';
36
36
  export { Translation, TranslationLine, TranslationBox } from './Translation';
37
- export { default as Spinner } from './Spinner';
38
37
  export { default as SearchResultSleeve } from './Search/SearchResultSleeve';
39
38
  export { default as ContentTypeResult } from './Search/ContentTypeResult';
40
39
  export { SearchFieldForm } from './Search/SearchFieldForm';
package/lib/index.js CHANGED
@@ -83,7 +83,6 @@ var _exportNames = {
83
83
  Translation: true,
84
84
  TranslationLine: true,
85
85
  TranslationBox: true,
86
- Spinner: true,
87
86
  SearchResultSleeve: true,
88
87
  ContentTypeResult: true,
89
88
  SearchFieldForm: true,
@@ -650,12 +649,6 @@ Object.defineProperty(exports, "TranslationBox", {
650
649
  return _Translation.TranslationBox;
651
650
  }
652
651
  });
653
- Object.defineProperty(exports, "Spinner", {
654
- enumerable: true,
655
- get: function get() {
656
- return _Spinner["default"];
657
- }
658
- });
659
652
  Object.defineProperty(exports, "SearchResultSleeve", {
660
653
  enumerable: true,
661
654
  get: function get() {
@@ -1336,8 +1329,6 @@ var _LearningPaths = require("./LearningPaths");
1336
1329
 
1337
1330
  var _Translation = require("./Translation");
1338
1331
 
1339
- var _Spinner = _interopRequireDefault(require("./Spinner"));
1340
-
1341
1332
  var _SearchResultSleeve = _interopRequireDefault(require("./Search/SearchResultSleeve"));
1342
1333
 
1343
1334
  var _ContentTypeResult = _interopRequireDefault(require("./Search/ContentTypeResult"));
@@ -62,6 +62,7 @@ declare const messages: {
62
62
  folder: string;
63
63
  delete: string;
64
64
  edit: string;
65
+ missingName: string;
65
66
  };
66
67
  confirmDeleteFolder: string;
67
68
  confirmDeleteTag: string;
@@ -93,7 +94,12 @@ declare const messages: {
93
94
  ask: string;
94
95
  };
95
96
  wishToDelete: string;
96
- terms: string;
97
+ terms: {
98
+ terms: string;
99
+ term1: string;
100
+ term2: string;
101
+ term3: string;
102
+ };
97
103
  feide: string;
98
104
  newFavourite: string;
99
105
  storageInfo: {
@@ -964,8 +970,10 @@ declare const messages: {
964
970
  open: string;
965
971
  close: string;
966
972
  };
973
+ cancel: string;
967
974
  close: string;
968
975
  title: string;
976
+ save: string;
969
977
  image: {
970
978
  altText: string;
971
979
  caption: string;
@@ -823,8 +823,10 @@ var messages = _objectSpread(_objectSpread({
823
823
  open: 'Open menu',
824
824
  close: 'Close menu'
825
825
  },
826
+ cancel: 'Cancel',
826
827
  close: 'Close',
827
828
  title: 'Title',
829
+ save: 'Save',
828
830
  image: {
829
831
  altText: 'Alt-text',
830
832
  caption: 'Caption',
@@ -954,7 +956,8 @@ var messages = _objectSpread(_objectSpread({
954
956
  folder: {
955
957
  folder: 'Folder',
956
958
  "delete": 'Delete',
957
- edit: 'Edit'
959
+ edit: 'Edit',
960
+ missingName: 'Folder name required'
958
961
  },
959
962
  confirmDeleteFolder: 'Are you sure you want to delete this folder? This process cannot be undone.',
960
963
  confirmDeleteTag: 'Are you sure you want to delete this tag? This process cannot be undone.',
@@ -986,7 +989,12 @@ var messages = _objectSpread(_objectSpread({
986
989
  ask: 'Ask us in the chat'
987
990
  },
988
991
  wishToDelete: 'Do you wish to delete your account?',
989
- terms: 'terms of use',
992
+ terms: {
993
+ terms: 'Terms of use',
994
+ term1: 'Do not write personal or sensitive information in text fields.',
995
+ term2: 'Do not write offensive statements in text fields.',
996
+ term3: 'NDLA reserves the right to update or remove resources if they are not up to date.'
997
+ },
990
998
  feide: 'We have retrieved this information from Feide',
991
999
  newFavourite: 'Recently favourited',
992
1000
  storageInfo: {
@@ -62,6 +62,7 @@ declare const messages: {
62
62
  folder: string;
63
63
  delete: string;
64
64
  edit: string;
65
+ missingName: string;
65
66
  };
66
67
  confirmDeleteFolder: string;
67
68
  confirmDeleteTag: string;
@@ -93,7 +94,12 @@ declare const messages: {
93
94
  ask: string;
94
95
  };
95
96
  wishToDelete: string;
96
- terms: string;
97
+ terms: {
98
+ terms: string;
99
+ term1: string;
100
+ term2: string;
101
+ term3: string;
102
+ };
97
103
  newFavourite: string;
98
104
  feide: string;
99
105
  storageInfo: {
@@ -966,6 +972,8 @@ declare const messages: {
966
972
  };
967
973
  close: string;
968
974
  title: string;
975
+ cancel: string;
976
+ save: string;
969
977
  image: {
970
978
  altText: string;
971
979
  caption: string;
@@ -825,6 +825,8 @@ var messages = _objectSpread(_objectSpread({
825
825
  },
826
826
  close: 'Lukk',
827
827
  title: 'Tittel',
828
+ cancel: 'Avbryt',
829
+ save: 'Lagre',
828
830
  image: {
829
831
  altText: 'Alt-tekst',
830
832
  caption: 'Bildetekst',
@@ -954,7 +956,8 @@ var messages = _objectSpread(_objectSpread({
954
956
  folder: {
955
957
  folder: 'Mappe',
956
958
  "delete": 'Slett',
957
- edit: 'Rediger'
959
+ edit: 'Rediger',
960
+ missingName: 'Mappenavn er påkrevd'
958
961
  },
959
962
  confirmDeleteFolder: 'Er du sikker på at du vil slette mappen? Denne handlingen kan ikke angres.',
960
963
  confirmDeleteTag: 'Er du sikker på at du vil slette tag? Denne handlingen kan ikke angres.',
@@ -986,7 +989,12 @@ var messages = _objectSpread(_objectSpread({
986
989
  ask: 'Spør oss i chatten'
987
990
  },
988
991
  wishToDelete: 'Ønsker du ikke ha brukerprofil hos oss lengre?',
989
- terms: 'vilkår for bruk',
992
+ terms: {
993
+ terms: 'Vilkår for bruk',
994
+ term1: 'Ikke skriv personsensitiv informasjon eller persondata i tekstfelt.',
995
+ term2: 'Ikke skriv noe støtende i tekstfelt.',
996
+ term3: 'NDLA forbeholder seg retten til å oppdatere eller eventuelt slette ressurser dersom disse blir utdatert.'
997
+ },
990
998
  newFavourite: 'Nylig lagt til',
991
999
  feide: 'Dette henter vi om deg fra Feide',
992
1000
  storageInfo: {
@@ -62,6 +62,7 @@ declare const messages: {
62
62
  folder: string;
63
63
  delete: string;
64
64
  edit: string;
65
+ missingName: string;
65
66
  };
66
67
  confirmDeleteFolder: string;
67
68
  confirmDeleteTag: string;
@@ -93,7 +94,12 @@ declare const messages: {
93
94
  ask: string;
94
95
  };
95
96
  wishToDelete: string;
96
- terms: string;
97
+ terms: {
98
+ terms: string;
99
+ term1: string;
100
+ term2: string;
101
+ term3: string;
102
+ };
97
103
  newFavourite: string;
98
104
  feide: string;
99
105
  storageInfo: {
@@ -964,8 +970,10 @@ declare const messages: {
964
970
  open: string;
965
971
  close: string;
966
972
  };
973
+ cancel: string;
967
974
  close: string;
968
975
  title: string;
976
+ save: string;
969
977
  image: {
970
978
  altText: string;
971
979
  caption: string;
@@ -823,8 +823,10 @@ var messages = _objectSpread(_objectSpread({
823
823
  open: 'Åpne meny',
824
824
  close: 'Lukk meny'
825
825
  },
826
+ cancel: 'Avbryt',
826
827
  close: 'Lukk',
827
828
  title: 'Tittel',
829
+ save: 'Lagre',
828
830
  image: {
829
831
  altText: 'Alt-tekst',
830
832
  caption: 'Bilettekst',
@@ -954,7 +956,8 @@ var messages = _objectSpread(_objectSpread({
954
956
  folder: {
955
957
  folder: 'Mappe',
956
958
  "delete": 'Slett',
957
- edit: 'Rediger'
959
+ edit: 'Rediger',
960
+ missingName: 'Mappenavn er påkrevd'
958
961
  },
959
962
  confirmDeleteFolder: 'Er du sikker på at du vil slette mappa? Denne handlinga kan ikkje angres.',
960
963
  confirmDeleteTag: 'Er du sikker på at du vil slette tag? Denne handlinga kan ikkje angres.',
@@ -986,7 +989,12 @@ var messages = _objectSpread(_objectSpread({
986
989
  ask: 'Spør oss i chatten'
987
990
  },
988
991
  wishToDelete: 'Ønsker du ikke ha brukerprofil hos oss lengre?',
989
- terms: 'vilkår for bruk',
992
+ terms: {
993
+ terms: 'Vilkår for bruk',
994
+ term1: 'Ikkje skriv personsensitiv informasjon eller persondata i tekstfelt.',
995
+ term2: 'Ikkje skriv noko støytande i tekstfelt.',
996
+ term3: 'NDLA atterhald seg retten til å oppdatere eller eventuelt slette ressursar dersom disse blir utdatert.'
997
+ },
990
998
  newFavourite: 'Nylig lagt til',
991
999
  feide: 'Dette henter vi om deg fra Feide',
992
1000
  storageInfo: {
@@ -62,6 +62,7 @@ declare const messages: {
62
62
  folder: string;
63
63
  delete: string;
64
64
  edit: string;
65
+ missingName: string;
65
66
  };
66
67
  confirmDeleteFolder: string;
67
68
  confirmDeleteTag: string;
@@ -93,7 +94,12 @@ declare const messages: {
93
94
  ask: string;
94
95
  };
95
96
  wishToDelete: string;
96
- terms: string;
97
+ terms: {
98
+ terms: string;
99
+ term1: string;
100
+ term2: string;
101
+ term3: string;
102
+ };
97
103
  newFavourite: string;
98
104
  feide: string;
99
105
  storageInfo: {
@@ -964,8 +970,10 @@ declare const messages: {
964
970
  open: string;
965
971
  close: string;
966
972
  };
973
+ cancel: string;
967
974
  close: string;
968
975
  title: string;
976
+ save: string;
969
977
  image: {
970
978
  altText: string;
971
979
  caption: string;
@@ -823,8 +823,10 @@ var messages = _objectSpread(_objectSpread({
823
823
  open: 'Åpne meny',
824
824
  close: 'Lukk meny'
825
825
  },
826
+ cancel: 'Avbryt',
826
827
  close: 'Lukk',
827
828
  title: 'Tittel',
829
+ save: 'Lagre',
828
830
  image: {
829
831
  altText: 'Alt-tekst',
830
832
  caption: 'Bilettekst',
@@ -954,7 +956,8 @@ var messages = _objectSpread(_objectSpread({
954
956
  folder: {
955
957
  folder: 'Mappe',
956
958
  "delete": 'Slett',
957
- edit: 'Rediger'
959
+ edit: 'Rediger',
960
+ missingName: 'Mappenavn er påkrevd'
958
961
  },
959
962
  confirmDeleteFolder: 'Er du sikker på at du vil slette mappen? Denne handlingen kan ikke angres.',
960
963
  confirmDeleteTag: 'Er du sikker på at du vil slette tag? Denne handlingen kan ikke angres.',
@@ -986,7 +989,12 @@ var messages = _objectSpread(_objectSpread({
986
989
  ask: 'Spør oss i chatten'
987
990
  },
988
991
  wishToDelete: 'Ønsker du ikke ha brukerprofil hos oss lengre?',
989
- terms: 'vilkår for bruk',
992
+ terms: {
993
+ terms: 'Vilkår for bruk',
994
+ term1: 'Ikke skriv personsensitiv informasjon eller persondata i tekstfelt.',
995
+ term2: 'Ikke skriv noe støtende i tekstfelt.',
996
+ term3: 'NDLA forbeholder seg retten til å oppdatere eller eventuelt slette ressurser dersom disse blir utdatert.'
997
+ },
990
998
  newFavourite: 'Nylig lagt til',
991
999
  feide: 'Dette henter vi om deg fra Feide',
992
1000
  storageInfo: {
@@ -62,6 +62,7 @@ declare const messages: {
62
62
  folder: string;
63
63
  delete: string;
64
64
  edit: string;
65
+ missingName: string;
65
66
  };
66
67
  confirmDeleteFolder: string;
67
68
  confirmDeleteTag: string;
@@ -93,7 +94,12 @@ declare const messages: {
93
94
  ask: string;
94
95
  };
95
96
  wishToDelete: string;
96
- terms: string;
97
+ terms: {
98
+ terms: string;
99
+ term1: string;
100
+ term2: string;
101
+ term3: string;
102
+ };
97
103
  newFavourite: string;
98
104
  feide: string;
99
105
  storageInfo: {
@@ -964,8 +970,10 @@ declare const messages: {
964
970
  open: string;
965
971
  close: string;
966
972
  };
973
+ cancel: string;
967
974
  close: string;
968
975
  title: string;
976
+ save: string;
969
977
  image: {
970
978
  altText: string;
971
979
  caption: string;
@@ -823,8 +823,10 @@ var messages = _objectSpread(_objectSpread({
823
823
  open: 'Åpne meny',
824
824
  close: 'Lukk meny'
825
825
  },
826
+ cancel: 'Avbryt',
826
827
  close: 'Lukk',
827
828
  title: 'Tittel',
829
+ save: 'Lagre',
828
830
  image: {
829
831
  altText: 'Alt-tekst',
830
832
  caption: 'Bilettekst',
@@ -954,7 +956,8 @@ var messages = _objectSpread(_objectSpread({
954
956
  folder: {
955
957
  folder: 'Mappe',
956
958
  "delete": 'Slett',
957
- edit: 'Rediger'
959
+ edit: 'Rediger',
960
+ missingName: 'Mappenavn er påkrevd'
958
961
  },
959
962
  confirmDeleteFolder: 'Er du sikker på at du vil slette mappen? Denne handlingen kan ikke angres.',
960
963
  confirmDeleteTag: 'Er du sikker på at du vil slette tag? Denne handlingen kan ikke angres.',
@@ -986,7 +989,12 @@ var messages = _objectSpread(_objectSpread({
986
989
  ask: 'Spør oss i chatten'
987
990
  },
988
991
  wishToDelete: 'Ønsker du ikke ha brukerprofil hos oss lengre?',
989
- terms: 'vilkår for bruk',
992
+ terms: {
993
+ terms: 'Vilkår for bruk',
994
+ term1: 'Ikke skriv personsensitiv informasjon eller persondata i tekstfelt.',
995
+ term2: 'Ikke skriv noe støtende i tekstfelt.',
996
+ term3: 'NDLA forbeholder seg retten til å oppdatere eller eventuelt slette ressurser dersom disse blir utdatert.'
997
+ },
990
998
  newFavourite: 'Nylig lagt til',
991
999
  feide: 'Dette henter vi om deg fra Feide',
992
1000
  storageInfo: {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ndla/ui",
3
- "version": "19.2.0",
3
+ "version": "20.0.3",
4
4
  "description": "UI component library for NDLA.",
5
5
  "license": "GPL-3.0",
6
6
  "main": "lib/index.js",
@@ -31,18 +31,19 @@
31
31
  "types"
32
32
  ],
33
33
  "dependencies": {
34
- "@ndla/button": "^3.1.2",
35
- "@ndla/carousel": "^1.2.11",
36
- "@ndla/core": "^2.3.0",
34
+ "@ndla/button": "^3.1.5",
35
+ "@ndla/carousel": "^1.2.14",
36
+ "@ndla/core": "^2.3.2",
37
+ "@ndla/forms": "^3.1.2",
37
38
  "@ndla/hooks": "^1.1.4",
38
- "@ndla/icons": "^1.10.0",
39
- "@ndla/licenses": "^5.0.2",
40
- "@ndla/modal": "^1.2.12",
41
- "@ndla/notion": "^3.1.22",
42
- "@ndla/safelink": "^2.2.0",
43
- "@ndla/switch": "^0.1.7",
44
- "@ndla/tabs": "^1.1.10",
45
- "@ndla/tooltip": "^2.1.2",
39
+ "@ndla/icons": "^1.11.2",
40
+ "@ndla/licenses": "^5.0.5",
41
+ "@ndla/modal": "^1.2.15",
42
+ "@ndla/notion": "^3.1.25",
43
+ "@ndla/safelink": "^2.2.3",
44
+ "@ndla/switch": "^0.1.9",
45
+ "@ndla/tabs": "^1.1.13",
46
+ "@ndla/tooltip": "^2.1.4",
46
47
  "@ndla/util": "^3.0.0",
47
48
  "@reach/menu-button": "^0.16.2",
48
49
  "@reach/slider": "^0.16.0",
@@ -81,5 +82,5 @@
81
82
  "publishConfig": {
82
83
  "access": "public"
83
84
  },
84
- "gitHead": "5f018a6a78778970d0d448896de96bb16e970fab"
85
+ "gitHead": "fd7915eee936f4d2450c1263e4830a7bda29d49a"
85
86
  }
@@ -76,6 +76,7 @@ export type StepProps = {
76
76
  };
77
77
 
78
78
  interface Props {
79
+ onToggleAddToFavorites?: () => void;
79
80
  learningsteps: StepProps[];
80
81
  name: string;
81
82
  lastUpdated: string;
@@ -109,6 +110,7 @@ const LearningPathMenu = ({
109
110
  learningPathURL,
110
111
  invertedStyle,
111
112
  cookies,
113
+ onToggleAddToFavorites,
112
114
  }: Props) => {
113
115
  const { t } = useTranslation();
114
116
  const [isOpen, toggleOpenState] = useState(false);
@@ -129,7 +131,13 @@ const LearningPathMenu = ({
129
131
  </StyledToggleMenubutton>
130
132
  </Tooltip>
131
133
  </div>
132
- <LearningPathMenuIntro isOpen={isOpen} name={name} invertedStyle={invertedStyle} />
134
+ <LearningPathMenuIntro
135
+ isOpen={isOpen}
136
+ name={name}
137
+ invertedStyle={invertedStyle}
138
+ id={learningPathId}
139
+ onToggleAddToFavorites={onToggleAddToFavorites}
140
+ />
133
141
  <LearningPathMenuContent
134
142
  learningsteps={learningsteps}
135
143
  learningPathId={learningPathId}
@@ -11,6 +11,7 @@ import styled from '@emotion/styled';
11
11
  import { css } from '@emotion/core';
12
12
  import { useTranslation } from 'react-i18next';
13
13
  import { colors, spacing, spacingUnit, fonts, typography, mq, breakpoints, animations } from '@ndla/core';
14
+ import { ArticleFavoritesButton } from '../Article';
14
15
 
15
16
  const StyledInfoHeader = styled.p`
16
17
  ${typography.smallHeading}
@@ -94,18 +95,30 @@ const StyledIntroHeader = styled.h1`
94
95
  margin: ${spacing.small} 0 ${spacing.normal};
95
96
  `;
96
97
 
98
+ const StyledRow = styled.div`
99
+ display: flex;
100
+ gap: ${spacing.small};
101
+ `;
102
+
97
103
  interface Props {
98
104
  isOpen: boolean;
99
105
  invertedStyle?: boolean;
100
106
  name: string;
107
+ onToggleAddToFavorites?: () => void;
108
+ id: number;
101
109
  }
102
110
 
103
- const LearningPathMenuIntro = ({ isOpen, name, invertedStyle }: Props) => {
111
+ const LearningPathMenuIntro = ({ isOpen, name, invertedStyle, onToggleAddToFavorites, id }: Props) => {
104
112
  const { t } = useTranslation();
105
113
  return (
106
114
  <StyledMenuIntro isOpen={isOpen} invertedStyle={invertedStyle}>
107
115
  <div>
108
- <StyledInfoHeader>{t('learningPath.youAreInALearningPath')}</StyledInfoHeader>
116
+ <StyledRow>
117
+ <StyledInfoHeader>{t('learningPath.youAreInALearningPath')}</StyledInfoHeader>
118
+ {onToggleAddToFavorites && (
119
+ <ArticleFavoritesButton onToggleAddToFavorites={onToggleAddToFavorites} articleId={id.toString()} />
120
+ )}
121
+ </StyledRow>
109
122
  <StyledIntroHeader>{name}</StyledIntroHeader>
110
123
  </div>
111
124
  </StyledMenuIntro>
@@ -95,7 +95,10 @@ export const Masthead = ({
95
95
  )}
96
96
  <div id="masthead" {...classes('', { fixed: !!fixed, infoContent: !!infoContent, ndlaFilm: !!ndlaFilm })}>
97
97
  {messages?.map((message) => (
98
- <MessageBanner showCloseButton={message.closable} onClose={() => onCloseAlert?.(message.number)}>
98
+ <MessageBanner
99
+ key={message.number}
100
+ showCloseButton={message.closable}
101
+ onClose={() => onCloseAlert?.(message.number)}>
99
102
  {message.content}
100
103
  </MessageBanner>
101
104
  ))}
@@ -24,7 +24,7 @@ const MessageBannerWrapper = styled.div<WrapperProps>`
24
24
  padding: ${({ small }) => (small ? spacing.xxsmall : spacing.small)};
25
25
  background: ${colors.support.yellowLight};
26
26
  color: ${colors.brand.greyDark};
27
- border: none;
27
+ border-bottom: solid 1px ${colors.white};
28
28
  `;
29
29
 
30
30
  const TextWrapper = styled.div`
@@ -10,24 +10,17 @@ import styled from '@emotion/styled';
10
10
  import { IconButton } from '@ndla/button';
11
11
  import { FolderOutlined } from '@ndla/icons/contentType';
12
12
  import { Cross } from '@ndla/icons/action';
13
- import React, { ChangeEvent, KeyboardEvent, useEffect, useRef, useState } from 'react';
13
+ import React, { ChangeEvent, KeyboardEvent, useRef, useState } from 'react';
14
14
  import { useTranslation } from 'react-i18next';
15
15
  import { colors, spacing } from '@ndla/core';
16
+ import { Input } from '@ndla/forms';
17
+ import { css } from '@emotion/core';
16
18
 
17
19
  // Source: https://kovart.github.io/dashed-border-generator/
18
20
  const borderStyle = `url("data:image/svg+xml,%3csvg width='100%25' height='100%25' xmlns='http://www.w3.org/2000/svg'%3e%3crect width='100%25' height='100%25' fill='none' stroke='${encodeURIComponent(
19
21
  colors.brand.tertiary,
20
22
  )}' stroke-width='2' stroke-dasharray='8%2c8' stroke-dashoffset='4' stroke-linecap='square'/%3e%3c/svg%3e")`;
21
23
 
22
- const FolderInputWrapper = styled.div`
23
- display: flex;
24
- flex-direction: row;
25
- align-items: center;
26
- padding: ${spacing.small};
27
-
28
- background-image: ${borderStyle};
29
- `;
30
-
31
24
  const StyledFolderIcon = styled.span`
32
25
  display: flex;
33
26
  padding: ${spacing.small};
@@ -38,29 +31,33 @@ const StyledFolderIcon = styled.span`
38
31
  }
39
32
  `;
40
33
 
41
- const StyledInput = styled.input`
42
- color: ${colors.brand.primary};
43
- outline: none;
34
+ const inputWrapperStyle = css`
35
+ padding: ${spacing.small};
36
+ background: none;
37
+ background-image: ${borderStyle};
44
38
  border: none;
45
- margin-right: auto;
46
- line-height: 1.75em;
39
+ `;
47
40
 
48
- ::selection {
49
- background: ${colors.brand.lighter};
41
+ const StyledInput = styled(Input)`
42
+ && {
43
+ line-height: 1.75em;
44
+ color: ${colors.brand.primary};
45
+ ::selection {
46
+ background: ${colors.brand.lighter};
47
+ }
50
48
  }
51
49
  `;
52
50
 
53
51
  interface Props {
54
52
  onAddFolder: (name: string) => void;
55
53
  onClose: () => void;
56
- autoFocus?: boolean;
54
+ autoSelect?: boolean;
57
55
  }
58
56
 
59
- const FolderInput = ({ onAddFolder, onClose, autoFocus }: Props) => {
57
+ const FolderInput = ({ onAddFolder, onClose, autoSelect }: Props) => {
60
58
  const { t } = useTranslation();
61
59
  const newFolderText = t('treeStructure.newFolder.defaultName');
62
60
  const [input, setInput] = useState<string>(newFolderText);
63
- const [mounted, setMounted] = useState(false);
64
61
  const inputRef = useRef<HTMLInputElement>(null);
65
62
 
66
63
  const handleInputChange = (e: ChangeEvent<HTMLInputElement>) => {
@@ -68,36 +65,36 @@ const FolderInput = ({ onAddFolder, onClose, autoFocus }: Props) => {
68
65
  };
69
66
 
70
67
  const onKeydown = (e: KeyboardEvent<HTMLInputElement>) => {
71
- if (e.key === 'Enter' && input) {
68
+ if (e.key === 'Enter' && input.trim()) {
72
69
  e.preventDefault();
73
70
  onAddFolder(input);
71
+ } else if (e.key === 'Escape') {
72
+ e.preventDefault();
73
+ onClose();
74
74
  }
75
75
  };
76
76
 
77
- useEffect(() => {
78
- if (mounted && autoFocus) {
79
- inputRef.current?.select();
80
- } else {
81
- setMounted(true);
82
- }
83
- }, [mounted, autoFocus]);
84
-
85
77
  return (
86
- <FolderInputWrapper>
87
- <StyledFolderIcon>
88
- <FolderOutlined />
89
- </StyledFolderIcon>
90
- <StyledInput
91
- ref={inputRef}
92
- value={input}
93
- onChange={handleInputChange}
94
- onKeyDown={onKeydown}
95
- aria-label={newFolderText}
96
- />
97
- <IconButton aria-label={t('close')} size="small" ghostPill onClick={onClose}>
98
- <Cross />
99
- </IconButton>
100
- </FolderInputWrapper>
78
+ <StyledInput
79
+ autoSelect={autoSelect}
80
+ customCss={inputWrapperStyle}
81
+ warningText={!input.trim() ? t('myNdla.folder.missingName') : undefined}
82
+ ref={inputRef}
83
+ value={input}
84
+ onChange={handleInputChange}
85
+ onKeyDown={onKeydown}
86
+ aria-label={newFolderText}
87
+ iconLeft={
88
+ <StyledFolderIcon>
89
+ <FolderOutlined />
90
+ </StyledFolderIcon>
91
+ }
92
+ iconRight={
93
+ <IconButton aria-label={t('close')} size="small" ghostPill onClick={onClose}>
94
+ <Cross />
95
+ </IconButton>
96
+ }
97
+ />
101
98
  );
102
99
  };
103
100
 
@@ -12,8 +12,8 @@ import styled from '@emotion/styled';
12
12
  import { css } from '@emotion/core';
13
13
  import { breakpoints, mq, spacing, spacingUnit, fonts, colors } from '@ndla/core';
14
14
  import SafeLink from '@ndla/safelink';
15
+ import { Spinner } from '@ndla/icons';
15
16
  import { OneColumn } from '../Layout';
16
- import Spinner from '../Spinner';
17
17
  import NavigationArrow, { StyledNavigationArrow } from './NavigationArrow';
18
18
  import SlideshowIndicator from './SlideshowIndicator';
19
19
  import { MovieType } from './types';
@@ -88,6 +88,7 @@ const StyledImageWrapper = styled.div<StyledImageProps>`
88
88
  width: 54px;
89
89
  height: 40px;
90
90
  }
91
+ overflow: hidden;
91
92
  `;
92
93
 
93
94
  const StyledImage = styled(Image)`