danholibraryjs 1.7.0 → 1.10.0

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 (68) hide show
  1. package/.gitattributes +2 -2
  2. package/dist/Classes/Events/Event.js +1 -1
  3. package/dist/Classes/Events/EventCollection.js +1 -1
  4. package/dist/Classes/Events/EventEmitter.d.ts +28 -4
  5. package/dist/Classes/Events/EventEmitter.js +24 -0
  6. package/dist/Classes/Time/Date.d.ts +5 -5
  7. package/dist/Classes/Time/Time.d.ts +3 -3
  8. package/dist/Classes/Time/TimeProperties.d.ts +2 -2
  9. package/dist/Classes/Time/TimeSpan.d.ts +1 -1
  10. package/dist/Classes/index.d.ts +1 -0
  11. package/dist/Classes/index.js +1 -0
  12. package/dist/Classes/store.d.ts +79 -0
  13. package/dist/Classes/store.js +84 -0
  14. package/dist/Extensions/Array.d.ts +8 -1
  15. package/dist/Extensions/Array.js +47 -10
  16. package/dist/Extensions/Document.d.ts +27 -0
  17. package/dist/Extensions/Document.js +32 -0
  18. package/dist/Extensions/Function.d.ts +14 -0
  19. package/dist/Extensions/Function.js +10 -0
  20. package/dist/Extensions/Map.d.ts +17 -1
  21. package/dist/Extensions/Map.js +24 -13
  22. package/dist/Extensions/Object/index.d.ts +49 -0
  23. package/dist/Extensions/Object/index.js +38 -0
  24. package/dist/Extensions/Object/properties.d.ts +28 -0
  25. package/dist/Extensions/Object/properties.js +20 -0
  26. package/dist/Extensions/String.d.ts +11 -1
  27. package/dist/Extensions/String.js +15 -7
  28. package/dist/Extensions/index.d.ts +5 -17
  29. package/dist/Extensions/index.js +8 -49
  30. package/dist/Functions/GetCSSProperty.d.ts +1 -1
  31. package/dist/Functions/GetNestedProperty.d.ts +9 -0
  32. package/dist/Functions/GetNestedProperty.js +23 -0
  33. package/dist/Functions/index.d.ts +1 -0
  34. package/dist/Functions/index.js +1 -0
  35. package/dist/Interfaces/ElementOptions.d.ts +4 -4
  36. package/dist/Types/BetterTypes.d.ts +3 -3
  37. package/dist/Types/Date.d.ts +6 -6
  38. package/dist/Types/Events.d.ts +2 -2
  39. package/dist/Types/PropertiesWith.d.ts +2 -2
  40. package/dist/Types/TransformTypes.d.ts +2 -2
  41. package/dist/Types/index.d.ts +21 -6
  42. package/docs/Classes.md +33 -0
  43. package/docs/Extensions.md +7 -0
  44. package/docs/Functions.md +8 -0
  45. package/docs/Types.md +30 -17
  46. package/package.json +6 -3
  47. package/src/Classes/Events/Event.ts +1 -1
  48. package/src/Classes/Events/EventCollection.ts +1 -1
  49. package/src/Classes/Events/EventEmitter.ts +40 -5
  50. package/src/Classes/index.ts +2 -1
  51. package/src/Classes/store.ts +98 -0
  52. package/src/Extensions/Array.ts +49 -11
  53. package/src/Extensions/Document.ts +58 -0
  54. package/src/Extensions/Function.ts +18 -0
  55. package/src/Extensions/Map.ts +24 -9
  56. package/src/Extensions/Object/index.ts +82 -0
  57. package/src/Extensions/Object/properties.ts +51 -0
  58. package/src/Extensions/String.ts +17 -6
  59. package/src/Extensions/index.ts +7 -66
  60. package/src/Functions/GetNestedProperty.ts +29 -0
  61. package/src/Functions/index.ts +1 -0
  62. package/src/Interfaces/ElementOptions.ts +2 -2
  63. package/src/Types/index.ts +27 -2
  64. package/tsconfig.json +2 -2
  65. package/Time.xlsx +0 -0
  66. package/dist/Extensions/Object.d.ts +0 -16
  67. package/dist/Extensions/Object.js +0 -8
  68. package/src/Extensions/Object.ts +0 -25
@@ -0,0 +1,38 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ObjectExtensions = void 0;
4
+ const properties_1 = require("./properties");
5
+ function array(from) {
6
+ return Object.keysOf(from).map(prop => [prop, from[prop]]);
7
+ }
8
+ Object.array = array;
9
+ function extract(from, ...props) {
10
+ // If props are Array<keyof From>, Array<Partial<From>>, or Array<keyof From | Partial<From>>, ensure _props as Array<keyof From>
11
+ const _props = props.map(prop => typeof prop === "object" ? Object.keysOf(prop) : prop).flat();
12
+ _props.forEach(prop => delete from[prop]);
13
+ return from;
14
+ }
15
+ Object.extract = extract;
16
+ function exclude(from, ...props) {
17
+ // If props are Array<keyof From>, Array<Partial<From>>, or Array<keyof From | Partial<From>>, ensure _props as Array<keyof From>
18
+ const _props = props.map(prop => typeof prop === "object" ? Object.keysOf(prop) : prop).flat();
19
+ return Object.keysOf(from).reduce((result, prop) => {
20
+ if (_props.includes(prop))
21
+ delete result[prop];
22
+ return result;
23
+ }, from);
24
+ }
25
+ Object.exclude = exclude;
26
+ function isNullOrUndefined(obj) {
27
+ return obj === null || obj === undefined;
28
+ }
29
+ Object.isNullOrUndefined = isNullOrUndefined;
30
+ function keysOf(from) {
31
+ return Object.keys(from);
32
+ }
33
+ Object.keysOf = keysOf;
34
+ Object.properties = properties_1.properties;
35
+ exports.ObjectExtensions = {
36
+ properties: properties_1.properties,
37
+ array, extract, exclude, isNullOrUndefined, keysOf,
38
+ };
@@ -0,0 +1,28 @@
1
+ import { PropertiesWith, If } from '../../Types';
2
+ type PrimitiveMap = {
3
+ string: string;
4
+ number: number;
5
+ boolean: boolean;
6
+ undefined: undefined;
7
+ null: null;
8
+ object: object;
9
+ function: Function;
10
+ any: any;
11
+ Date: Date;
12
+ RegExp: RegExp;
13
+ Promise: Promise<any>;
14
+ Array: Array<any>;
15
+ Map: Map<any, any>;
16
+ Set: Set<any>;
17
+ };
18
+ /**
19
+ * Object with getPrimitiveTypes<Source, AllowFunctions extends boolean>(
20
+ * source: Source,
21
+ * allowFunctions: AllowFunctions = false
22
+ * ): Object with properties from source that matches primitive type
23
+ */
24
+ export type Properties = {
25
+ [Key in keyof PrimitiveMap as `get${Capitalize<Key>}s`]: <Source extends {}, AllowFunctions extends boolean = false>(source: Source, withFunctions?: AllowFunctions) => If<AllowFunctions, PropertiesWith<PrimitiveMap[Key] | ((...args: any[]) => PrimitiveMap[Key]), Source>, PropertiesWith<PrimitiveMap[Key], Source>>;
26
+ };
27
+ export declare const properties: Properties;
28
+ export {};
@@ -0,0 +1,20 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.properties = void 0;
4
+ const String_1 = require("../String");
5
+ exports.properties = [
6
+ 'string', 'number', 'boolean', 'undefined', 'null',
7
+ 'object', 'function', 'any',
8
+ 'Date', 'RegExp', 'Promise', 'Array', 'Map', 'Set'
9
+ ].reduce((result, primitive) => {
10
+ result[`get${String_1.StringExtensions.toPascalCase.bind(primitive)()}s`] = function (source, withFunctions = false) {
11
+ return Object.keysOf(source).reduce((result, key) => {
12
+ if (source[key].constructor.name === primitive ||
13
+ (withFunctions && typeof source[key] === 'function' && source[key]).constructor.name === primitive) {
14
+ result[key] = source[key];
15
+ }
16
+ return result;
17
+ }, {});
18
+ };
19
+ return result;
20
+ }, {});
@@ -1,5 +1,4 @@
1
1
  import IReplacement from "../Interfaces/IReplacement";
2
- export {};
3
2
  declare global {
4
3
  interface String {
5
4
  /**
@@ -24,3 +23,14 @@ declare global {
24
23
  clip(start: number, end?: number): string;
25
24
  }
26
25
  }
26
+ declare function toPascalCase(this: string): string;
27
+ declare function toSnakeCase(this: string, replaceOptions: IReplacement): string;
28
+ declare function toKebabCase(this: string, replaceOptions: IReplacement): string;
29
+ declare function clip(this: string, start: number, end?: number): string;
30
+ export declare const StringExtensions: {
31
+ toPascalCase: typeof toPascalCase;
32
+ toSnakeCase: typeof toSnakeCase;
33
+ toKebabCase: typeof toKebabCase;
34
+ clip: typeof clip;
35
+ };
36
+ export {};
@@ -1,17 +1,25 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- String.prototype.toPascalCase = function () {
3
+ exports.StringExtensions = void 0;
4
+ function toPascalCase() {
4
5
  return this.substring(0, 1).toUpperCase() + this.substring(1);
5
- };
6
+ }
7
+ String.prototype.toPascalCase = toPascalCase;
6
8
  function spaceReplacer(self, replacer, replacement) {
7
9
  return self.replace(new RegExp(`${typeof replacer == 'string' ? replacer : replacer.source}+`), replacement);
8
10
  }
9
- String.prototype.toSnakeCase = function (replaceOptions) {
11
+ function toSnakeCase(replaceOptions) {
10
12
  return spaceReplacer(this, replaceOptions.replacer || ' ', replaceOptions.replacement || '_');
11
- };
12
- String.prototype.toKebabCase = function (replaceOptions) {
13
+ }
14
+ String.prototype.toSnakeCase = toSnakeCase;
15
+ function toKebabCase(replaceOptions) {
13
16
  return spaceReplacer(this, replaceOptions.replacer || ' ', replaceOptions.replacement || '-');
14
- };
15
- String.prototype.clip = function (start, end) {
17
+ }
18
+ String.prototype.toKebabCase = toKebabCase;
19
+ function clip(start, end) {
16
20
  return this.substring(start < 0 ? this.length - start : start, end && end < 0 ? this.length + end : end);
21
+ }
22
+ String.prototype.clip = clip;
23
+ exports.StringExtensions = {
24
+ toPascalCase, toSnakeCase, toKebabCase, clip
17
25
  };
@@ -1,6 +1,5 @@
1
- import ElementOptions from "../Interfaces/ElementOptions";
2
- import { IElement } from "../Types";
3
1
  export * from './Array';
2
+ export * from './Document';
4
3
  export * from './Map';
5
4
  export * from './Object';
6
5
  export * from './String';
@@ -11,19 +10,8 @@ declare global {
11
10
  */
12
11
  parseBoolean(value: string): boolean;
13
12
  }
14
- interface Document {
15
- /**
16
- * Creates an element like Document#createElement, however with construction options to assign values in construction instead of after construction.
17
- * @param tagName HTMLElement tag name
18
- * @param options Construction options, instead of assigning values after construction
19
- */
20
- createProperElement<K extends keyof HTMLElementTagNameMap>(tagName: K, options?: ElementOptions, ...children: Array<IElement>): HTMLElementTagNameMap[K];
21
- createFromHtml<K extends keyof HTMLElementTagNameMap>(html: string, parentTag?: K): HTMLElementTagNameMap[K];
22
- }
23
- interface HTMLCollection {
24
- /**
25
- * Converts HTMLCollection to Element[]
26
- */
27
- array(): Element[];
28
- }
29
13
  }
14
+ declare function parseBoolean(value: string): boolean;
15
+ export declare const BooleanExtensions: {
16
+ parseBoolean: typeof parseBoolean;
17
+ };
@@ -14,58 +14,17 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
14
  for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
15
  };
16
16
  Object.defineProperty(exports, "__esModule", { value: true });
17
+ exports.BooleanExtensions = void 0;
17
18
  __exportStar(require("./Array"), exports);
19
+ __exportStar(require("./Document"), exports);
18
20
  __exportStar(require("./Map"), exports);
19
21
  __exportStar(require("./Object"), exports);
20
22
  __exportStar(require("./String"), exports);
21
- Boolean.parseBoolean = function (value) {
23
+ function parseBoolean(value) {
22
24
  return value === "true";
23
- };
24
- try {
25
- Document.prototype.createProperElement = function (tagName, options, ...children) {
26
- let baseElement = document.createElement(tagName);
27
- if (!options)
28
- return baseElement;
29
- const { id, class: className, dataset, ...rest } = options;
30
- if (id)
31
- baseElement.id = id;
32
- if (className) {
33
- const classNames = Array.isArray(className) ? className : [className];
34
- classNames.forEach(className => baseElement.classList.add(className));
35
- }
36
- children ?? options.children;
37
- if (children) {
38
- const childrenElements = Array.isArray(children) ? children : [children];
39
- childrenElements.forEach(child => baseElement.append(child));
40
- }
41
- if (dataset)
42
- Object.entries(dataset).forEach(([key, value]) => baseElement.dataset[key] = value);
43
- for (const optionKey in rest) {
44
- const optionValue = rest[optionKey];
45
- if (optionValue === undefined)
46
- continue;
47
- if (typeof optionValue === 'function') {
48
- baseElement.addEventListener(optionKey.substring(2), rest[optionKey]);
49
- }
50
- else {
51
- baseElement.setAttribute(optionKey, optionValue.toString());
52
- }
53
- }
54
- return baseElement;
55
- };
56
- Document.prototype.createFromHtml = function (html, parentTag) {
57
- return new DOMParser().parseFromString(html, 'text/html').body.firstChild;
58
- };
59
- HTMLCollection.prototype.array = function () {
60
- let result = new Array();
61
- for (let i = 0; i < this.length; i++) {
62
- const item = this.item(i);
63
- if (item !== null)
64
- result.push(item);
65
- }
66
- return result;
67
- };
68
- }
69
- catch {
70
- // Used in node.js
71
25
  }
26
+ ;
27
+ Boolean.parseBoolean = parseBoolean;
28
+ exports.BooleanExtensions = {
29
+ parseBoolean
30
+ };
@@ -1,4 +1,4 @@
1
- declare type CSSReturnTypes = {
1
+ type CSSReturnTypes = {
2
2
  string: string;
3
3
  number: number;
4
4
  };
@@ -0,0 +1,9 @@
1
+ export type GetNestedProperty<Parent, Key extends string> = Key extends keyof Parent ? Parent[Key] : Key extends `${infer K}.${infer Rest}` ? K extends keyof Parent ? GetNestedProperty<Parent[K], Rest> : never : never;
2
+ /**
3
+ * Gets a nested property from an object
4
+ * @param parent Parent object to search
5
+ * @param key Key to search for. Can be nested with dot notation
6
+ * @returns Value of key or null if not found
7
+ */
8
+ export declare function GetNestedProperty<Parent extends object, Key extends string>(parent: Parent, key: Key): GetNestedProperty<Parent, Key> | null;
9
+ export default GetNestedProperty;
@@ -0,0 +1,23 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.GetNestedProperty = void 0;
4
+ /**
5
+ * Gets a nested property from an object
6
+ * @param parent Parent object to search
7
+ * @param key Key to search for. Can be nested with dot notation
8
+ * @returns Value of key or null if not found
9
+ */
10
+ function GetNestedProperty(parent, key) {
11
+ if (key in parent)
12
+ return parent[key];
13
+ for (const prop in parent) {
14
+ if (typeof parent[prop] === 'object') {
15
+ const result = GetNestedProperty(parent[prop], key);
16
+ if (result)
17
+ return result;
18
+ }
19
+ }
20
+ return null;
21
+ }
22
+ exports.GetNestedProperty = GetNestedProperty;
23
+ exports.default = GetNestedProperty;
@@ -1,4 +1,5 @@
1
1
  export * from './CopyToClipboard';
2
2
  export * from './GetCSSProperty';
3
+ export * from './GetNestedProperty';
3
4
  export * from './SetNavigationSelected';
4
5
  export * from './HTMLEvent';
@@ -16,5 +16,6 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
16
16
  Object.defineProperty(exports, "__esModule", { value: true });
17
17
  __exportStar(require("./CopyToClipboard"), exports);
18
18
  __exportStar(require("./GetCSSProperty"), exports);
19
+ __exportStar(require("./GetNestedProperty"), exports);
19
20
  __exportStar(require("./SetNavigationSelected"), exports);
20
21
  __exportStar(require("./HTMLEvent"), exports);
@@ -1,14 +1,14 @@
1
1
  import { Arrayable, IElement } from "../Types";
2
- declare type Events = Record<`on${Capitalize<keyof HTMLElementEventMap>}`, (event: Event) => void>;
2
+ type Events = Record<`on${Capitalize<keyof HTMLElementEventMap>}`, (event: Event) => void>;
3
3
  /**
4
4
  * Construction options when creating an HTML element using:
5
- * @see Document.createProperElement
5
+ * @see Document.createElement
6
6
  * @borwwos IElement
7
7
  * @borrows Arrayable
8
8
  */
9
- export declare type ElementOptions = Partial<Events & Record<string, any> & {
9
+ export type ElementOptions = Partial<Events & Record<string, any> & {
10
10
  id: string;
11
- class: Arrayable<string>;
11
+ className: Arrayable<string>;
12
12
  children: Arrayable<IElement>;
13
13
  dataset: Record<string, string>;
14
14
  }>;
@@ -1,9 +1,9 @@
1
1
  /**
2
2
  * Construct a type with the properties of Type except for those in type Properties.
3
3
  */
4
- export declare type BetterOmit<Type, Properties extends keyof Type> = Omit<Type, Properties>;
4
+ export type BetterOmit<Type, Properties extends keyof Type> = Omit<Type, Properties>;
5
5
  /**
6
6
  * Extract from From those types that are assignable to Properties
7
7
  */
8
- export declare type BetterExtract<From, Properties extends From> = Extract<From, Properties>;
9
- export declare type PartialExcept<From, Properties extends keyof From> = Partial<From> & Required<Pick<From, Properties>>;
8
+ export type BetterExtract<From, Properties extends From> = Extract<From, Properties>;
9
+ export type PartialExcept<From, Properties extends keyof From> = Partial<From> & Required<Pick<From, Properties>>;
@@ -1,6 +1,6 @@
1
- export declare type LongMonth = 'Janurary' | 'February' | 'March' | 'April' | 'May' | 'June' | 'July' | 'August' | 'September' | 'October' | 'November' | 'December';
2
- export declare type ShortMonth = 'Jan' | 'Feb' | 'Mar' | 'Apr' | 'May' | 'Jun' | 'Jul' | 'Aug' | 'Sep' | 'Oct' | 'Nov' | 'Dec';
3
- export declare type Month = LongMonth | ShortMonth;
4
- export declare type ShortDay = 'Mon' | 'Tue' | 'Wed' | 'Thu' | 'Fri' | 'Sat' | 'Sun';
5
- export declare type LongDay = `${'Mon' | 'Tues' | 'Wednes' | 'Thurs' | 'Fri' | 'Satur' | 'Sun'}day`;
6
- export declare type Day = ShortDay | LongDay;
1
+ export type LongMonth = 'Janurary' | 'February' | 'March' | 'April' | 'May' | 'June' | 'July' | 'August' | 'September' | 'October' | 'November' | 'December';
2
+ export type ShortMonth = 'Jan' | 'Feb' | 'Mar' | 'Apr' | 'May' | 'Jun' | 'Jul' | 'Aug' | 'Sep' | 'Oct' | 'Nov' | 'Dec';
3
+ export type Month = LongMonth | ShortMonth;
4
+ export type ShortDay = 'Mon' | 'Tue' | 'Wed' | 'Thu' | 'Fri' | 'Sat' | 'Sun';
5
+ export type LongDay = `${'Mon' | 'Tues' | 'Wednes' | 'Thurs' | 'Fri' | 'Satur' | 'Sun'}day`;
6
+ export type Day = ShortDay | LongDay;
@@ -1,10 +1,10 @@
1
1
  /**
2
2
  * Default eventhandler mapper. Object with properties that are arrays
3
3
  */
4
- export declare type BaseEvent<Keys extends string, Types extends Array<any>> = Record<Keys, Types>;
4
+ export type BaseEvent<Keys extends string, Types extends Array<any>> = Record<Keys, Types>;
5
5
  /**
6
6
  * Eventhandler type for:
7
7
  * @see EventCollection
8
8
  * @borrows BaseEvent
9
9
  */
10
- export declare type EventHandler<Events extends BaseEvent<string, Array<any>> = BaseEvent<string, Array<any>>, Event extends keyof Events = keyof Events, ReturnType = any> = (...args: Events[Event]) => ReturnType;
10
+ export type EventHandler<Events extends BaseEvent<string, Array<any>> = BaseEvent<string, Array<any>>, Event extends keyof Events = keyof Events, ReturnType = any> = (...args: Events[Event]) => ReturnType;
@@ -1,13 +1,13 @@
1
1
  /**
2
2
  * Filters all properties from From that has the return type of Type
3
3
  */
4
- export declare type PropertiesWith<Type, From> = {
4
+ export type PropertiesWith<Type, From> = {
5
5
  [Key in keyof From as From[Key] extends Type ? Key : never]: From[Key];
6
6
  };
7
7
  export default PropertiesWith;
8
8
  /**
9
9
  * Fitlers all properties from From that don't have the return type of Type
10
10
  */
11
- export declare type PropertiesWithout<Type, From> = {
11
+ export type PropertiesWithout<Type, From> = {
12
12
  [Key in keyof From as From[Key] extends Type ? never : Key]: From[Key];
13
13
  };
@@ -1,13 +1,13 @@
1
1
  /**
2
2
  * Converts Start types to Switch types in From type
3
3
  */
4
- export declare type TransformType<From, Start, Switch> = {
4
+ export type TransformType<From, Start, Switch> = {
5
5
  [Key in keyof From]: From[Key] extends Start ? Switch : From[Key];
6
6
  };
7
7
  /**
8
8
  * Returns object with properties matching BaseType with types of NewType
9
9
  */
10
- export declare type TransformTypes<From, BaseType, NewType> = Record<keyof {
10
+ export type TransformTypes<From, BaseType, NewType> = Record<keyof {
11
11
  [Key in keyof From as From[Key] extends BaseType ? Key : never]: Key;
12
12
  }, NewType>;
13
13
  export default TransformTypes;
@@ -6,26 +6,41 @@ export * from './PropertiesWith';
6
6
  /**
7
7
  * Item is single or multiple
8
8
  */
9
- export declare type Arrayable<T> = T | Array<T>;
9
+ export type Arrayable<T> = T | Array<T>;
10
+ /**
11
+ * Item is function or T
12
+ */
13
+ export type Functionable<T> = T | (() => T);
14
+
10
15
  /**
11
16
  * Used for HTMLElement.append in ElementOptions, Document.createProperElement.
12
17
  * IElement accepts HTML Elements or HTMl-like strings.
13
18
  *
14
19
  * @see HTMLElement.append
15
- * @see Document.createProperElement
20
+ * @see Document.createElement
16
21
  */
17
- export declare type IElement = HTMLElement | string;
22
+ export type IElement = HTMLElement | string;
18
23
  /**
19
24
  * Return types of T
20
25
  */
21
- export declare type ValueOf<T> = T[keyof T];
26
+ export type ValueOf<T> = T[keyof T];
22
27
  /**
23
28
  * Type's properties are ReturnType
24
29
  */
25
- export declare type AllPropsAre<ReturnType> = {
30
+ export type AllPropsAre<ReturnType> = {
26
31
  [key: string]: ReturnType;
27
32
  };
28
33
  /**
29
34
  * string or RegExp.. pretty self-explanatory
30
35
  */
31
- export declare type StringRegex = string | RegExp;
36
+ export type StringRegex = string | RegExp;
37
+ export type If<Boolean extends boolean, True, False> = Boolean extends true ? True : False;
38
+ /**
39
+ * GetRepeatedKeys<[
40
+ * { username: string, password: string },
41
+ * { username: number, email: string },
42
+ * ]> // { username: string | number }
43
+ */
44
+ export type GetRepeatedKeys<Types extends Array<any>> = (Types extends [infer First, infer Second, ...infer Rest] ? First extends object ? Second extends object ? {
45
+ [Key in Extract<keyof First, keyof Second>]: First[Key] | Second[Key];
46
+ } & GetRepeatedKeys<Rest> : {} : {} : {});
package/docs/Classes.md CHANGED
@@ -2,6 +2,39 @@
2
2
 
3
3
  ## Classes
4
4
 
5
+ ```ts
6
+ /**
7
+ * EventEmitter, but it stores state and handles state change with reducers
8
+ *
9
+ * @Initialization Actions & initial state must be defined in type parameters. InitialState must be provided in constructor, whereas reducer is optional.
10
+ * The ActionType must have properties as strings and values as arrays.
11
+ *
12
+ * @HandlingActions Reducers can be added through constructor or using Store.on('action', reducer) or Store.once('action', reducer).
13
+ * Every state change must return the next state, apart from 'stateChange', which returns void/any
14
+ * Emit/Dispatch an action using Store.dispatch('action', ...args), ...args being the parameters from the ActionType.
15
+ * Store.emit should NOT be used, as it doesn't update the Store's state.
16
+ *
17
+ * Reducer functions can be removed using Store.off('action', reducer);
18
+ *
19
+ * @borrows EventEmitter
20
+ * @borrows Arrayable
21
+ */
22
+ class Store<
23
+ State extends object,
24
+ ActionTypes extends Record<string, any[]>,
25
+ Actions extends
26
+ { [Action in keyof ActionTypes]: Array<Reducer<State, ActionTypes, Action>> } =
27
+ { [Action in keyof ActionTypes]: Array<Reducer<State, ActionTypes, Action>> }
28
+ > extends EventEmitter<Record<keyof Actions, ActionTypes[keyof ActionTypes]> & Record<'stateChange', [previous: State, current: State]>> {
29
+ constructor(state: State, actions: { [Action in keyof ActionTypes]?: Arrayable<Reducer<State, ActionTypes, Action>> } = {});
30
+
31
+ private _state: State;
32
+ public get state(): State;
33
+
34
+ public dispatch<Action extends keyof ActionTypes>(action: Action, ...args: ActionTypes[Action]): State;
35
+ }
36
+ ```
37
+
5
38
  ### Events
6
39
 
7
40
  ```ts
@@ -58,6 +58,13 @@ interface Array<T> {
58
58
  * @param i Index of item
59
59
  */
60
60
  index(i: number): T
61
+ /**
62
+ * For every number in array, do callback
63
+ * @param every For every x in array
64
+ * @param callback Do this for every x in array
65
+ * @returns Mapped array
66
+ */
67
+ nth<U>(every: number, callback: (collection: Array<T>, index: number, self: this) => U): Array<U>
61
68
  }
62
69
  ```
63
70
 
package/docs/Functions.md CHANGED
@@ -21,6 +21,14 @@ async function CopyToClipboard(value: string, response?: string): Promise<void>;
21
21
  */
22
22
  function GetCSSProperty<Type extends keyof CSSReturnTypes>(property: string, type: Type, query = ":root"): CSSReturnTypes[Type];
23
23
 
24
+ /**
25
+ * Gets a nested property from an object
26
+ * @param parent Parent object to search
27
+ * @param key Key to search for. Can be nested with dot notation
28
+ * @returns Value of key or null if not found
29
+ */
30
+ function GetNestedProperty<Parent, Key extends string>(parent: Parent, key: Key): GetNestedProperty<Parent, Key> | null;
31
+
24
32
  /**
25
33
  * Create HTMLEvent object from function
26
34
  * @param name Name of the event
package/docs/Types.md CHANGED
@@ -8,14 +8,19 @@
8
8
  /**
9
9
  * Type's properties are ReturnType
10
10
  */
11
- export type AllPropsAre<ReturnType> = {
11
+ type AllPropsAre<ReturnType> = {
12
12
  [key: string]: ReturnType
13
13
  }
14
14
 
15
15
  /**
16
16
  * Item is single or multiple
17
17
  */
18
- export type Arrayable<T> = T | Array<T>;
18
+ type Arrayable<T> = T | Array<T>;
19
+
20
+ /**
21
+ * If Condition is true, Then, Else... pretty self-explanatory
22
+ */
23
+ type If<Condition, Then, Else> = Condition extends true ? Then : Else;
19
24
 
20
25
  /**
21
26
  * Used for HTMLElement.append in ElementOptions, Document.createProperElement.
@@ -24,17 +29,17 @@ export type Arrayable<T> = T | Array<T>;
24
29
  * @see HTMLElement.append
25
30
  * @see Document.createProperElement
26
31
  */
27
- export type IElement = HTMLElement | string;
32
+ type IElement = HTMLElement | string;
28
33
 
29
34
  /**
30
35
  * string or RegExp.. pretty self-explanatory
31
36
  */
32
- export type StringRegex = string | RegExp;
37
+ type StringRegex = string | RegExp;
33
38
 
34
39
  /**
35
40
  * Return types of T
36
41
  */
37
- export type ValueOf<T> = T[keyof T];
42
+ type ValueOf<T> = T[keyof T];
38
43
  ```
39
44
 
40
45
  ### BetterTypes
@@ -43,11 +48,11 @@ export type ValueOf<T> = T[keyof T];
43
48
  /**
44
49
  * Construct a type with the properties of Type except for those in type Properties.
45
50
  */
46
- export type BetterOmit<Type, Properties extends keyof Type> = Omit<Type, Properties>;
51
+ type BetterOmit<Type, Properties extends keyof Type> = Omit<Type, Properties>;
47
52
  /**
48
53
  * Extract from From those types that are assignable to Properties
49
54
  */
50
- export type BetterExtract<From, Properties extends From> = Extract<From, Properties>;
55
+ type BetterExtract<From, Properties extends From> = Extract<From, Properties>;
51
56
  ```
52
57
 
53
58
  ### Events
@@ -56,14 +61,14 @@ export type BetterExtract<From, Properties extends From> = Extract<From, Propert
56
61
  /**
57
62
  * Default eventhandler mapper. Object with properties that are arrays
58
63
  */
59
- export type BaseEvent<Keys extends string, Types extends Array<any>> = Record<Keys, Types>;
64
+ type BaseEvent<Keys extends string, Types extends Array<any>> = Record<Keys, Types>;
60
65
 
61
66
  /**
62
67
  * Eventhandler type for:
63
68
  * @see EventCollection
64
69
  * @borrows BaseEvent
65
70
  */
66
- export type EventHandler<
71
+ type EventHandler<
67
72
  Events extends BaseEvent<string, Array<any>> = BaseEvent<string, Array<any>>,
68
73
  Event extends keyof Events = keyof Events,
69
74
  ReturnType = any
@@ -76,15 +81,15 @@ export type BetterExtract<From, Properties extends From> = Extract<From, Propert
76
81
  /**
77
82
  * Filters all properties from From that has the return type of Type
78
83
  */
79
- export type PropertiesWith<Type, From> = {
84
+ type PropertiesWith<Type, From> = {
80
85
  [Key in keyof From as From[Key] extends Type ? Key : never]: From[Key]
81
86
  }
82
- export default PropertiesWith;
87
+ default PropertiesWith;
83
88
 
84
89
  /**
85
90
  * Fitlers all properties from From that don't have the return type of Type
86
91
  */
87
- export type PropertiesWithout<Type, From> = {
92
+ type PropertiesWithout<Type, From> = {
88
93
  [Key in keyof From as From[Key] extends Type ? never : Key]: From[Key]
89
94
  }
90
95
  ```
@@ -97,17 +102,17 @@ export type PropertiesWithout<Type, From> = {
97
102
  * @Data Partial TimeProperties except years & months
98
103
  * @DateFormat string as dd/MM/yyyy
99
104
  */
100
- export type DanhoDateConstructor = Data | DateFormat | number | Date;
105
+ type DanhoDateConstructor = Data | DateFormat | number | Date;
101
106
 
102
107
  /**
103
108
  * Object interface with keys above to number values. If Plural is true, all properties ends with 's'
104
109
  */
105
- export type TimeProperties<Plural extends boolean = false> = Record<Plural extends true ? `${TimeKeys}s` : TimeKeys, number>
110
+ type TimeProperties<Plural extends boolean = false> = Record<Plural extends true ? `${TimeKeys}s` : TimeKeys, number>
106
111
 
107
112
  /**
108
113
  * What properties to include when using TimeSpan.toString(format: TimeSpanFormat): string
109
114
  */
110
- export type TimeSpanFormat = Partial<TransformType<TimeProperties<true>, number, boolean>>
115
+ type TimeSpanFormat = Partial<TransformType<TimeProperties<true>, number, boolean>>
111
116
  ```
112
117
 
113
118
  ### TransformTypes
@@ -116,14 +121,22 @@ export type TimeSpanFormat = Partial<TransformType<TimeProperties<true>, number,
116
121
  /**
117
122
  * Converts Start types to Switch types in From type
118
123
  */
119
- export type TransformType<From, Start, Switch> = {
124
+ type TransformType<From, Start, Switch> = {
120
125
  [Key in keyof From]: From[Key] extends Start ? Switch : From[Key]
121
126
  }
122
127
 
123
128
  /**
124
129
  * Returns object with properties matching BaseType with types of NewType
125
130
  */
126
- export type TransformTypes<From, BaseType, NewType> = Record<keyof {
131
+ type TransformTypes<From, BaseType, NewType> = Record<keyof {
127
132
  [Key in keyof From as From[Key] extends BaseType ? Key : never]: Key
128
133
  }, NewType>
129
134
  ```
135
+
136
+ ### Store
137
+ ```ts
138
+ /**
139
+ * Reducer function to map wanted parameters when using @see Store.on(action, reducer);
140
+ */
141
+ type Reducer<State, Types extends Record<string, any[]>, Action extends keyof Types> = (state: State, ...args: Types[Action]) => State
142
+ ```