Skip to content

Commit 83b6d36

Browse files
committed
Fix broken "rule" entrypoint on "typesVersions" in package.json
Add entrypoint "file" to package.json Add src/formats/file/index.ts to define all public file manipulation functions
1 parent 346028e commit 83b6d36

File tree

4 files changed

+196
-174
lines changed

4 files changed

+196
-174
lines changed

CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,12 @@ Add support for CommonJS modules through editing the "exports" package.json fiel
1818

1919
Add default export of functions in src/formats/rule/index.ts
2020

21+
Fix broken "rule" entrypoint on "typesVersions" in package.json
22+
23+
Add entrypoint "file" to package.json
24+
25+
Add src/formats/file/index.ts to define all public file manipulation functions
26+
2127
## April 10: Version 0.1.4
2228

2329
Bump to version 0.1.4

package.json

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,13 +43,20 @@
4343
"./rule": {
4444
"default": "./dist/formats/rule/index.js",
4545
"types": "./dist/types/formats/rule/index.d.ts"
46+
},
47+
"./file": {
48+
"default": "./dist/formats/file/index.js",
49+
"types": "./dist/types/formats/file/index.d.ts"
4650
}
4751
},
4852
"typesVersions": {
4953
"*": {
5054
"*": ["./dist/types/api.d.ts"],
5155
"rule": [
52-
"./dist/types/formats/rule.d.ts"
56+
"./dist/types/formats/rule/index.d.ts"
57+
],
58+
"file": [
59+
"./dist/types/formats/file/index.d.ts"
5360
]
5461
}
5562
},

src/api.ts

Lines changed: 2 additions & 173 deletions
Original file line numberDiff line numberDiff line change
@@ -7,183 +7,12 @@
77
* @license MIT
88
*/
99

10-
import { readLife106String, isLife106String, writeLife106String, Life106DecodedData, Life106EncodingData } from "./formats/file/life106"
11-
import { readPlaintextString, isPlaintextString, PlaintextDecodedData, PlaintextMatrixWriteData, PlaintextCoordinateWriteData, writePlaintextString } from "./formats/file/plaintext"
12-
import { RLECoordinateEncodingData, RLEDecodedData, RLEMatrixEncodingData, isRLEString, readRLEString, writeRLEString } from "./formats/file/rle"
13-
import { Life105DecodedData, isLife105String, readLife105String } from "./formats/file/life105"
1410
import { readLifeRule, makeLifeRule, isValidLifeRule, getLifeRuleFormat } from "./formats/rule"
11+
import { readLifeString, writeLifeString, isLifeStringFormat, getLifeStringFormat } from "./formats/file"
1512

1613
export { LifeRuleData, CONWAY_LIFE_RULE_DATA } from "./formats/rule/ruleData"
1714
export { readLifeRule, makeLifeRule, isValidLifeRule, getLifeRuleFormat } from "./formats/rule"
18-
19-
20-
21-
type SupportedLifeLikeFormats = "life 1.06" | "life 1.05" | "plaintext" | "rle"
22-
23-
/**
24-
* Read a life string
25-
*
26-
* A life string can be in either one of these formats.
27-
*
28-
* [Life 1.05](https://conwaylife.com/wiki/Life_1.05):
29-
* represented by the string "life 1.05"
30-
*
31-
* [Life 1.06](https://conwaylife.com/wiki/Life_1.06):
32-
* represented by the string "life 1.06"
33-
*
34-
* [Plaintext](https://conwaylife.com/wiki/Plaintext):
35-
* represented by the string "plaintext"
36-
*
37-
* [Run-Length Encoded (RLE)](https://conwaylife.com/wiki/Run_Length_Encoded).
38-
* represented by the string "rle"
39-
*
40-
* @note Usually these files are generated by a Life-Like program, such as Golly or XLife,
41-
* or by a library such as llcacodec. However, they can be written by hand if you so please.
42-
*
43-
* The output of the given data object is based on which one of the formats is parsed. However, all returned data
44-
* is guaranteed to have 2 keys: "format" and "liveCoordinates".
45-
*
46-
* The parsed format can be found with the "format" key,
47-
* which will either have a value of "plaintext", "life 1.06", "life 1.05", or "rle" corresponding with the given life string's format.
48-
* The layout of the parsed data can then be determined by finding the value of the "format" key.
49-
*
50-
* "liveCoordinates" will be a 2D vector array in [x, y] format where each entry represents a live cell.
51-
* x and y are guaranteed to be integers.
52-
* x is positive to the right and negative approaching the left, and y is positive approaching north and
53-
* negative approaching south. This may be good to take note of if your program assumes that positive
54-
* y approaches south, such as in a "row" and "column" layout.
55-
*
56-
* The particulars of each data format is out of the scope of this little docstring,
57-
* and can be found in DOCUMENTATION.md in the llcacodec repository. This documentation
58-
* could also be found online [here](https://www.github.com/cobyj33/llcacodec/blob/master/DOCUMENTATION.md)
59-
*
60-
* @param data The life string to parse for data
61-
* @param format Optional parameter. Defaults to "" if no parameter is passed. This is the format
62-
* used by readLifeString to parse the data. format can equal either "life 1.06", "life 1.05",
63-
* "plaintext", "rle", or "". If format equals "", then readLifeString will attempt to detect
64-
* the format of the provided data. If undefined is passed, an error is thrown
65-
*
66-
* @throws 1. If there is an error parsing the given life string in a given format.
67-
* 2. If there is an error finding the life string's format.
68-
* 3. If the passed format is undefined.
69-
*/
70-
export function readLifeString(data: string, format: "plaintext"): PlaintextDecodedData
71-
export function readLifeString(data: string, format: "life 1.06"): Life106DecodedData
72-
export function readLifeString(data: string, format: "rle"): RLEDecodedData
73-
export function readLifeString(data: string, format: "life 1.05"): Life105DecodedData
74-
export function readLifeString(data: string): Life106DecodedData | PlaintextDecodedData | RLEDecodedData | Life105DecodedData
75-
export function readLifeString(data: string, format: SupportedLifeLikeFormats | "" = ""): Life106DecodedData | PlaintextDecodedData | RLEDecodedData | Life105DecodedData {
76-
if (format === undefined) {
77-
throw new Error("[llcacodec]: Cannot parse undefined life file")
78-
}
79-
80-
const foundFormat = format === "" ? getLifeStringFormat(data) : format;
81-
switch (foundFormat) {
82-
case "plaintext": return readPlaintextString(data);
83-
case "life 1.06": return readLife106String(data);
84-
case "rle": return readRLEString(data);
85-
case "life 1.05": return readLife105String(data);
86-
case "": throw new Error(`[llcacodecjs] Could not read life file: matching life file format could not be found`)
87-
}
88-
}
89-
90-
/**
91-
* Assert whether a life string conforms to a given format
92-
*
93-
* Note that just because isLifeStringFormat returns true does NOT mean that readLifeString will not throw an error when called with the given life string.
94-
* isLifeStringFormat does not confirm if the passed data is valid. It only tries to detect if the given life string
95-
* conforms to a format by searching for required headers and sequences in the string.
96-
*
97-
* @param data The life string to test
98-
* @param format The format to test conformity against the given life string with.
99-
* Can either be "plaintext", "life 1.05", "life 1.06", or "plaintext"
100-
* @returns Whether the given life string conforms with the given format
101-
*/
102-
export function isLifeStringFormat(data: string, format: SupportedLifeLikeFormats): boolean {
103-
switch (format) {
104-
case "life 1.06": return isLife106String(data);
105-
case "life 1.05": return isLife105String(data);
106-
case "plaintext": return isPlaintextString(data);
107-
case "rle": return isRLEString(data);
108-
}
109-
}
110-
111-
/** Detect the format of a life string
112-
*
113-
* Note that just because getLifeStringFormat detects a file format does NOT mean that readLifeString will not throw an error
114-
* when called with the given life string. getLifeStringFormat does not confirm if the passed data is valid.
115-
* It only tries to detect the given life string's format by searching for required headers and sequences in the string.
116-
*
117-
* @param data The life string to get the format of
118-
* @returns Either "life 1.06", "life 1.05", "rle", or "plaintext" on the finding
119-
* of a successful format, and an empty string when no format could be found.
120-
*/
121-
export function getLifeStringFormat(data: string): SupportedLifeLikeFormats | "" {
122-
// Note how the tests are ordered. They are ordered from the most simple to identify
123-
// to the least simple to identify. Life 1.06 and Life 1.05 can simply be identified by
124-
// if their file begins with the appropriate header data. isRLEString is identified by the existence of
125-
// a header, although it may not be at the beginning of the file. Finally, Plaintext is identified by simply
126-
// checking if the file parses correctly
127-
128-
if (isLife106String(data)) {
129-
return "life 1.06"
130-
} else if (isLife105String(data)) {
131-
return "life 1.05"
132-
} else if (isRLEString(data)) {
133-
return "rle"
134-
} else if (isPlaintextString(data)) {
135-
return "plaintext"
136-
}
137-
138-
return ""
139-
}
140-
141-
type FileFormatData = ( Life106EncodingData & { format: "life 1.06"} ) |
142-
( PlaintextMatrixWriteData & { format: "plaintext"} ) |
143-
( PlaintextCoordinateWriteData & { format: "plaintext"} ) |
144-
( RLEMatrixEncodingData & { format: "rle" } ) |
145-
( RLECoordinateEncodingData & { format: "rle" })
146-
147-
/**
148-
* Write a Life String, keeping the passed data in a portable string format
149-
*
150-
* writeLifeString can write in either one of these formats:
151-
*
152-
* [Life 1.06](https://conwaylife.com/wiki/Life_1.06):
153-
* represented by the presence of { format: "life 1.06" } in the given structured data
154-
*
155-
* [Plaintext](https://conwaylife.com/wiki/Plaintext):
156-
* represented by the presence of { format: "plaintext" } in the given structured data
157-
*
158-
* [Run-Length Encoded (RLE)](https://conwaylife.com/wiki/Run_Length_Encoded):
159-
* represented by the presence of { format: "rle" } in the given structured data
160-
*
161-
* Given all of these formats, rle will likely be the most compressed and desired
162-
* format the large majority of the time. Generally, it is much better to represent
163-
* any semi-large or large pattern, but it is less straight-forward for humans to read
164-
* if that is desired.
165-
*
166-
* Plaintext will be a little larger, but should generally not be used for patterns with a bounding box with a width
167-
* greater than 80 cells. Plaintext, however, could be desired for smaller patterns because of
168-
* the human-readability of the pattern's diagram.
169-
*
170-
* Life 1.06 is also viable for smaller patterns. However, since Life 1.06 lists every single
171-
* coordinate without any compression, Life 1.06 could make for larger files as well.
172-
*
173-
* The particulars of each data format is out of the scope of this little docstring,
174-
* and can be found in DOCUMENTATION.md in the llcacodec repository. This documentation
175-
* could also be found online [here](https://www.github.com/cobyj33/llcacodec/blob/master/DOCUMENTATION.md)
176-
*
177-
* @param data The structured data to use when creating the life string
178-
* @returns A life string containing the passed in compiled data.
179-
*/
180-
export function writeLifeString(data: FileFormatData): string {
181-
switch (data.format) {
182-
case "life 1.06": return writeLife106String(data);
183-
case "plaintext": return writePlaintextString(data);
184-
case "rle": return writeRLEString(data)
185-
}
186-
}
15+
export { readLifeString, writeLifeString, isLifeStringFormat, getLifeStringFormat } from "./formats/file"
18716

18817
export default {
18918
readLifeString,

0 commit comments

Comments
 (0)