label-studio-converter 1.5.0 → 1.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/README.md CHANGED
@@ -249,10 +249,10 @@ label-studio-converter --help
249
249
  ```
250
250
  USAGE
251
251
  label-studio-converter toLabelStudio [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] [--defaultLabelName value] [--toFullJson] [--createFilePerImage] [--createFileListForServing] [--fileListName value] [--baseServerUrl value] [--outputMode value] <args>...
252
- label-studio-converter toPPOCR [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] [--baseImageDir value] <args>...
252
+ label-studio-converter toPPOCR [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] [--baseImageDir value] [--generateFileState] <args>...
253
253
  label-studio-converter enhance-labelstudio [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] [--outputMode value] <args>...
254
254
  label-studio-converter enhance-ppocr [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] <args>...
255
- label-studio-converter label-studio-output-to-ppocr [--recursive] (--outDir value) [--fileName value] [--removeBaseImageDir value] <args>...
255
+ label-studio-converter label-studio-output-to-ppocr [--recursive] [--backup] [--filePattern value] (--outDir value) [--fileName value] [--removeBaseImageDir value] [--generateFileState] <args>...
256
256
  label-studio-converter --help
257
257
  label-studio-converter --version
258
258
 
@@ -267,7 +267,7 @@ COMMANDS
267
267
  toPPOCR Convert Label Studio files to PPOCRLabel format
268
268
  enhance-labelstudio Enhance Label Studio files with sorting, normalization, and resizing
269
269
  enhance-ppocr Enhance PPOCRLabel files with sorting, normalization, and resizing
270
- label-studio-output-to-ppocr Convert Label Studio output files to PPOCRLabel format Enhance PPOCRLabel files with sorting, normalization, and resizing
270
+ label-studio-output-to-ppocr Convert Label Studio output files to PPOCRLabel format
271
271
  ```
272
272
 
273
273
  #### Command Flags Reference
@@ -477,6 +477,13 @@ COMMANDS
477
477
  - **Example**: `--baseImageDir "images/ch"` writes `images/ch/example.jpg` in
478
478
  Label.txt
479
479
 
480
+ - `--generateFileState` / `--noGenerateFileState`: Generate file state
481
+ - **Behavior**: Creates `fileState.txt` for each input directory, listing all
482
+ processed files
483
+ - **Default**: `true`
484
+ - **Example**: `--generateFileState` creates `fileState.txt` in each input
485
+ directory
486
+
480
487
  ##### Flags Specific to enhance-labelstudio Command
481
488
 
482
489
  - `--outputMode <mode>`: Same as toLabelStudio command
@@ -492,6 +499,13 @@ COMMANDS
492
499
  - **Example**: `--removeBaseImageDir "data/"` converts `data/example.jpg` to
493
500
  `example.jpg` in Label.txt
494
501
 
502
+ - `--generateFileState` / `--noGenerateFileState`: Generate file state
503
+ - **Behavior**: Creates `fileState.txt` for each input directory, listing all
504
+ processed files
505
+ - **Default**: `true`
506
+ - **Example**: `--generateFileState` creates `fileState.txt` in each input
507
+ directory
508
+
495
509
  #### Image Path Resolution Logic
496
510
 
497
511
  Understanding how image paths are resolved is critical for organizing your files before conversion. The key is knowing **where you run the command** and **what input parameter you provide**.
@@ -875,6 +889,7 @@ output/example.jpg [{"transcription":"Text","points":[[...]],"dt_score":1}]
875
889
  **OUTPUT Resolution**:
876
890
 
877
891
  - Generates PPOCRLabel Label.txt with `folder/filename.jpg` format
892
+ - Generates fileState.txt if `--generateFileState` is specified
878
893
 
879
894
  ---
880
895
 
@@ -978,7 +993,7 @@ label-studio-converter toPPOCR --help
978
993
 
979
994
  ```
980
995
  USAGE
981
- label-studio-converter toPPOCR [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] [--baseImageDir value] <args>...
996
+ label-studio-converter toPPOCR [--outDir value] [--fileName value] [--backup] [--recursive] [--filePattern value] [--copyImages] [--imageBaseDir value] [--sortVertical value] [--sortHorizontal value] [--normalizeShape value] [--useOrientedBox] [--widthIncrement value] [--heightIncrement value] [--adaptResize] [--adaptResizeThreshold value] [--adaptResizeMargin value] [--adaptResizeMinComponentSize value] [--adaptResizeMaxComponentSize value] [--adaptResizeOutlierPercentile value] [--adaptResizeMorphologySize value] [--adaptResizeMaxHorizontalExpansion value] [--adaptResizePaddingCheckWidth value] [--adaptResizeMinPaddingBrightness value] [--adaptResizeMinPaddingRatio value] [--adaptResizeUseAdaptiveThreshold] [--adaptResizeAdaptiveBlockSize value] [--precision value] [--baseImageDir value] [--generateFileState] <args>...
982
997
  label-studio-converter toPPOCR --help
983
998
 
984
999
  Convert Label Studio files to PPOCRLabel format
@@ -1012,6 +1027,7 @@ FLAGS
1012
1027
  [--adaptResizeAdaptiveBlockSize] Block size for adaptive thresholding. Default: 50
1013
1028
  [--precision] Number of decimal places for coordinates. Use -1 for full precision (no rounding). Default: 0 (integers)
1014
1029
  [--baseImageDir] Base directory path to prepend to image filenames in output (e.g., "ch" or "images/ch")
1030
+ [--generateFileState/--noGenerateFileState] Generate a file state file for each input directory
1015
1031
  -h --help Print help information and exit
1016
1032
 
1017
1033
  ARGUMENTS
@@ -1127,19 +1143,20 @@ label-studio-converter label-studio-output-to-ppocr --help
1127
1143
 
1128
1144
  ```
1129
1145
  USAGE
1130
- label-studio-converter label-studio-output-to-ppocr [--recursive] [--backup] [--filePattern value] (--outDir value) [--fileName value] [--removeBaseImageDir value] <args>...
1146
+ label-studio-converter label-studio-output-to-ppocr [--recursive] [--backup] [--filePattern value] (--outDir value) [--fileName value] [--removeBaseImageDir value] [--generateFileState] <args>...
1131
1147
  label-studio-converter label-studio-output-to-ppocr --help
1132
1148
 
1133
1149
  Convert Label Studio output files to PPOCRLabel format
1134
1150
 
1135
1151
  FLAGS
1136
- [--recursive/--noRecursive] Recursively search directories for files. Default: false
1137
- [--backup/--noBackup] Create backup of existing files before overwriting. Default: false
1138
- [--filePattern] Regex pattern to match input files
1139
- --outDir Output directory.
1140
- [--fileName] Output PPOCR file name. Default: "Label.txt"
1141
- [--removeBaseImageDir] Remove base image directory from image paths in output. Default: "/data/local-files/?d="
1142
- -h --help Print help information and exit
1152
+ [--recursive/--noRecursive] Recursively search directories for files. Default: false
1153
+ [--backup/--noBackup] Create backup of existing files before overwriting. Default: false
1154
+ [--filePattern] Regex pattern to match input files
1155
+ --outDir Output directory.
1156
+ [--fileName] Output PPOCR file name. Default: "Label.txt"
1157
+ [--removeBaseImageDir] Remove base image directory from image paths in output. Default: "/data/local-files/?d="
1158
+ [--generateFileState/--noGenerateFileState] Generate a file state file for each input directory
1159
+ -h --help Print help information and exit
1143
1160
 
1144
1161
  ARGUMENTS
1145
1162
  args... Input directories containing Label Studio files
@@ -38,7 +38,7 @@ var init_cjs_shims = __esm({
38
38
  });
39
39
 
40
40
  // src/constants.ts
41
- var DEFAULT_DETECT_IMAGE_SIZE, DEFAULT_LABEL_NAME, DEFAULT_LABEL_STUDIO_FULL_JSON, DEFAULT_CREATE_FILE_PER_IMAGE, DEFAULT_CREATE_FILE_LIST_FOR_SERVING, DEFAULT_FILE_LIST_NAME, DEFAULT_BASE_SERVER_URL, DEFAULT_PPOCR_FILE_NAME, SORT_VERTICAL_NONE, SORT_VERTICAL_TOP_BOTTOM, SORT_VERTICAL_BOTTOM_TOP, DEFAULT_SORT_VERTICAL, SORT_HORIZONTAL_NONE, SORT_HORIZONTAL_LTR, SORT_HORIZONTAL_RTL, DEFAULT_SORT_HORIZONTAL, SHAPE_NORMALIZE_NONE, SHAPE_NORMALIZE_RECTANGLE, DEFAULT_SHAPE_NORMALIZE, DEFAULT_USE_ORIENTED_BOX, DEFAULT_WIDTH_INCREMENT, DEFAULT_HEIGHT_INCREMENT, DEFAULT_ADAPT_RESIZE, DEFAULT_ADAPT_RESIZE_THRESHOLD, DEFAULT_ADAPT_RESIZE_MARGIN, DEFAULT_ADAPT_RESIZE_MIN_COMPONENT_SIZE, DEFAULT_ADAPT_RESIZE_MAX_COMPONENT_SIZE, DEFAULT_ADAPT_RESIZE_OUTLIER_PERCENTILE, DEFAULT_ADAPT_RESIZE_MORPHOLOGY_SIZE, DEFAULT_ADAPT_RESIZE_MAX_HORIZONTAL_EXPANSION, DEFAULT_ADAPT_RESIZE_TIMEOUT_MS, DEFAULT_ADAPT_RESIZE_MAX_BOX_SIZE, DEFAULT_ADAPT_RESIZE_PADDING_CHECK_WIDTH, DEFAULT_ADAPT_RESIZE_MIN_PADDING_BRIGHTNESS, DEFAULT_ADAPT_RESIZE_MIN_PADDING_RATIO, DEFAULT_ADAPT_RESIZE_USE_ADAPTIVE_THRESHOLD, DEFAULT_ADAPT_RESIZE_ADAPTIVE_BLOCK_SIZE, DEFAULT_LABEL_STUDIO_PRECISION, DEFAULT_PPOCR_PRECISION, DEFAULT_RECURSIVE, DEFAULT_PPOCR_FILE_PATTERN, DEFAULT_LABEL_STUDIO_FILE_PATTERN, OUTPUT_MODE_ANNOTATIONS, OUTPUT_MODE_PREDICTIONS, DEFAULT_OUTPUT_MODE, DEFAULT_BACKUP, BACKUP_SUFFIX_PREFIX, DEFAULT_COPY_IMAGES, IMAGE_BASE_DIR_TASK_FILE, IMAGE_BASE_DIR_INPUT_DIR, DEFAULT_IMAGE_BASE_DIR, DEFAULT_LABEL_STUDIO_OUTPUT_IMAGE_BASE_DIR;
41
+ var DEFAULT_DETECT_IMAGE_SIZE, DEFAULT_LABEL_NAME, DEFAULT_LABEL_STUDIO_FULL_JSON, DEFAULT_CREATE_FILE_PER_IMAGE, DEFAULT_CREATE_FILE_LIST_FOR_SERVING, DEFAULT_FILE_LIST_NAME, DEFAULT_BASE_SERVER_URL, DEFAULT_PPOCR_FILE_NAME, SORT_VERTICAL_NONE, SORT_VERTICAL_TOP_BOTTOM, SORT_VERTICAL_BOTTOM_TOP, DEFAULT_SORT_VERTICAL, SORT_HORIZONTAL_NONE, SORT_HORIZONTAL_LTR, SORT_HORIZONTAL_RTL, DEFAULT_SORT_HORIZONTAL, SHAPE_NORMALIZE_NONE, SHAPE_NORMALIZE_RECTANGLE, DEFAULT_SHAPE_NORMALIZE, DEFAULT_USE_ORIENTED_BOX, DEFAULT_WIDTH_INCREMENT, DEFAULT_HEIGHT_INCREMENT, DEFAULT_ADAPT_RESIZE, DEFAULT_ADAPT_RESIZE_THRESHOLD, DEFAULT_ADAPT_RESIZE_MARGIN, DEFAULT_ADAPT_RESIZE_MIN_COMPONENT_SIZE, DEFAULT_ADAPT_RESIZE_MAX_COMPONENT_SIZE, DEFAULT_ADAPT_RESIZE_OUTLIER_PERCENTILE, DEFAULT_ADAPT_RESIZE_MORPHOLOGY_SIZE, DEFAULT_ADAPT_RESIZE_MAX_HORIZONTAL_EXPANSION, DEFAULT_ADAPT_RESIZE_TIMEOUT_MS, DEFAULT_ADAPT_RESIZE_MAX_BOX_SIZE, DEFAULT_ADAPT_RESIZE_PADDING_CHECK_WIDTH, DEFAULT_ADAPT_RESIZE_MIN_PADDING_BRIGHTNESS, DEFAULT_ADAPT_RESIZE_MIN_PADDING_RATIO, DEFAULT_ADAPT_RESIZE_USE_ADAPTIVE_THRESHOLD, DEFAULT_ADAPT_RESIZE_ADAPTIVE_BLOCK_SIZE, DEFAULT_LABEL_STUDIO_PRECISION, DEFAULT_PPOCR_PRECISION, DEFAULT_RECURSIVE, DEFAULT_PPOCR_FILE_PATTERN, DEFAULT_LABEL_STUDIO_FILE_PATTERN, OUTPUT_MODE_ANNOTATIONS, OUTPUT_MODE_PREDICTIONS, DEFAULT_OUTPUT_MODE, DEFAULT_BACKUP, BACKUP_SUFFIX_PREFIX, DEFAULT_COPY_IMAGES, IMAGE_BASE_DIR_TASK_FILE, IMAGE_BASE_DIR_INPUT_DIR, DEFAULT_IMAGE_BASE_DIR, DEFAULT_LABEL_STUDIO_OUTPUT_IMAGE_BASE_DIR, DEFAULT_GENERATE_FILE_STATE;
42
42
  var init_constants = __esm({
43
43
  "src/constants.ts"() {
44
44
  "use strict";
@@ -95,6 +95,7 @@ var init_constants = __esm({
95
95
  IMAGE_BASE_DIR_INPUT_DIR = "input-dir";
96
96
  DEFAULT_IMAGE_BASE_DIR = IMAGE_BASE_DIR_TASK_FILE;
97
97
  DEFAULT_LABEL_STUDIO_OUTPUT_IMAGE_BASE_DIR = "/data/local-files/?d=";
98
+ DEFAULT_GENERATE_FILE_STATE = true;
98
99
  }
99
100
  });
100
101
 
@@ -268,6 +269,15 @@ function tupleToPoints(tuples) {
268
269
  function pointsToTuple(points) {
269
270
  return points.map(({ x, y }) => [x, y]);
270
271
  }
272
+ function polyToPoints(tuples, original_width, original_height) {
273
+ if (original_width && original_height) {
274
+ return tuples.map(([x, y]) => ({
275
+ x: x / 100 * original_width,
276
+ y: y / 100 * original_height
277
+ }));
278
+ }
279
+ return tupleToPoints(tuples);
280
+ }
271
281
  function rectangleToPoints(x, y, width, height, original_width, original_height) {
272
282
  if (original_width && original_height) {
273
283
  x = x / 100 * original_width;
@@ -1508,7 +1518,7 @@ var init_input = __esm({
1508
1518
  for (const item of items) {
1509
1519
  baseAnno = { ...baseAnno, ...item.value };
1510
1520
  }
1511
- let newPoints = "points" in baseAnno ? tupleToPoints(baseAnno.points) : [];
1521
+ let newPoints = "points" in baseAnno ? polyToPoints(baseAnno.points, imgWidth, imgHeight) : [];
1512
1522
  if (newPoints.length === 0 && "x" in baseAnno && "y" in baseAnno && "width" in baseAnno && "height" in baseAnno) {
1513
1523
  newPoints = rectangleToPoints(
1514
1524
  baseAnno.x,
@@ -1873,8 +1883,11 @@ var init_input4 = __esm({
1873
1883
  "use strict";
1874
1884
  init_cjs_shims();
1875
1885
  import_es_toolkit3 = require("es-toolkit");
1886
+ init_constants();
1876
1887
  init_geometry();
1877
- OutputLabelStudioInput = (async (inputTask, resolveImagePath) => {
1888
+ init_image();
1889
+ OutputLabelStudioInput = (async (inputTask, resolveImagePath, options) => {
1890
+ const { autoDetectImageSize = DEFAULT_DETECT_IMAGE_SIZE } = options || {};
1878
1891
  const imageFilePath = await resolveImagePath(inputTask.task.data.ocr);
1879
1892
  const { id, result, ...metadata } = inputTask;
1880
1893
  const annoData = result;
@@ -1882,6 +1895,17 @@ var init_input4 = __esm({
1882
1895
  (item) => item.original_height !== void 0 && item.original_width !== void 0
1883
1896
  );
1884
1897
  let { original_height: imgHeight, original_width: imgWidth } = imageMeta ?? {};
1898
+ if (autoDetectImageSize && (!imgHeight || !imgWidth)) {
1899
+ const dimensions = await getImageDimensions(imageFilePath);
1900
+ if (dimensions) {
1901
+ imgHeight = dimensions.height;
1902
+ imgWidth = dimensions.width;
1903
+ } else {
1904
+ console.warn(
1905
+ `Failed to auto-detect image size for ${imageFilePath}, using existing or 0x0`
1906
+ );
1907
+ }
1908
+ }
1885
1909
  const groupByAnnoId = (0, import_es_toolkit3.groupBy)(annoData || [], (item) => item.id);
1886
1910
  return {
1887
1911
  id: id.toString(),
@@ -1894,15 +1918,13 @@ var init_input4 = __esm({
1894
1918
  for (const item of items) {
1895
1919
  baseAnno = { ...baseAnno, ...item.value };
1896
1920
  }
1897
- let newPoints = "points" in baseAnno ? tupleToPoints(baseAnno.points) : [];
1921
+ let newPoints = "points" in baseAnno ? polyToPoints(baseAnno.points, imgWidth, imgHeight) : [];
1898
1922
  if (newPoints.length === 0 && "x" in baseAnno && "y" in baseAnno && "width" in baseAnno && "height" in baseAnno) {
1899
1923
  newPoints = rectangleToPoints(
1900
1924
  baseAnno.x,
1901
1925
  baseAnno.y,
1902
1926
  baseAnno.width,
1903
- baseAnno.height,
1904
- imgWidth,
1905
- imgHeight
1927
+ baseAnno.height
1906
1928
  );
1907
1929
  }
1908
1930
  return {
@@ -2995,7 +3017,8 @@ async function convertToPPOCR(flags, ...inputDirs) {
2995
3017
  adaptResizeMaxHorizontalExpansion = DEFAULT_ADAPT_RESIZE_MAX_HORIZONTAL_EXPANSION,
2996
3018
  precision = DEFAULT_PPOCR_PRECISION,
2997
3019
  recursive = DEFAULT_RECURSIVE,
2998
- filePattern = DEFAULT_LABEL_STUDIO_FILE_PATTERN
3020
+ filePattern = DEFAULT_LABEL_STUDIO_FILE_PATTERN,
3021
+ generateFileState = DEFAULT_GENERATE_FILE_STATE
2999
3022
  } = flags;
3000
3023
  console.log(import_chalk.default.blue("Finding files..."));
3001
3024
  const filePaths = await findFiles(inputDirs, filePattern, recursive);
@@ -3110,6 +3133,17 @@ async function convertToPPOCR(flags, ...inputDirs) {
3110
3133
  }
3111
3134
  await (0, import_promises4.writeFile)(outputPath, outputLines.join("\n"), "utf-8");
3112
3135
  console.log(import_chalk.default.green(`\u2713 Converted "${file}" -> "${outputPath}"`));
3136
+ if (generateFileState) {
3137
+ const fileStateLines = [];
3138
+ for (const task of outputTasks) {
3139
+ fileStateLines.push(`${task.imagePath} 1`);
3140
+ }
3141
+ const fileStatePath = (0, import_path6.join)(outputSubDir, `fileState.txt`);
3142
+ await (0, import_promises4.writeFile)(fileStatePath, fileStateLines.join("\n"), "utf-8");
3143
+ console.log(
3144
+ import_chalk.default.green(`\u2713 Generated file state: "${fileStatePath}"`)
3145
+ );
3146
+ }
3113
3147
  } catch (error) {
3114
3148
  console.error(
3115
3149
  import_chalk.default.red(`\u2717 Failed to process "${file}":`),
@@ -3428,7 +3462,8 @@ async function labelStudioOutputToPPOCR(flags, ...inputDirs) {
3428
3462
  backup = DEFAULT_BACKUP,
3429
3463
  recursive = DEFAULT_RECURSIVE,
3430
3464
  filePattern = void 0,
3431
- removeBaseImageDir = DEFAULT_LABEL_STUDIO_OUTPUT_IMAGE_BASE_DIR
3465
+ removeBaseImageDir = DEFAULT_LABEL_STUDIO_OUTPUT_IMAGE_BASE_DIR,
3466
+ generateFileState = DEFAULT_GENERATE_FILE_STATE
3432
3467
  } = flags;
3433
3468
  console.log(import_chalk4.default.blue("Finding files..."));
3434
3469
  const filePaths = await findFiles(inputDirs, filePattern, recursive);
@@ -3485,6 +3520,15 @@ async function labelStudioOutputToPPOCR(flags, ...inputDirs) {
3485
3520
  }
3486
3521
  }
3487
3522
  await (0, import_promises7.writeFile)(outputPath, outputLines.join("\n"), "utf-8");
3523
+ if (generateFileState) {
3524
+ const fileStateLines = [];
3525
+ for (const task of tasks) {
3526
+ fileStateLines.push(`${task.imagePath} 1`);
3527
+ }
3528
+ const fileStatePath = (0, import_path9.join)(outputImageDir, `fileState.txt`);
3529
+ await (0, import_promises7.writeFile)(fileStatePath, fileStateLines.join("\n"), "utf-8");
3530
+ console.log(import_chalk4.default.green(`\u2713 Generated file state: "${fileStatePath}"`));
3531
+ }
3488
3532
  }
3489
3533
  console.log(import_chalk4.default.green("\n\u2713 Conversion completed!"));
3490
3534
  }
@@ -3773,7 +3817,7 @@ var import_auto_complete = require("@stricli/auto-complete");
3773
3817
  var import_core6 = require("@stricli/core");
3774
3818
 
3775
3819
  // package.json
3776
- var version = "1.5.0";
3820
+ var version = "1.5.1";
3777
3821
  var description = "Convert between Label Studio OCR format and PPOCRLabelv2 format";
3778
3822
 
3779
3823
  // src/commands/enhance-labelstudio/command.ts
@@ -3903,6 +3947,11 @@ var labelStudioOutputToPPOCRCommand = (0, import_core3.buildCommand)({
3903
3947
  parse: String,
3904
3948
  brief: `Remove base image directory from image paths in output. Default: "${DEFAULT_LABEL_STUDIO_OUTPUT_IMAGE_BASE_DIR}"`,
3905
3949
  optional: true
3950
+ },
3951
+ generateFileState: {
3952
+ kind: "boolean",
3953
+ brief: "Generate a file state file for each input directory",
3954
+ optional: true
3906
3955
  }
3907
3956
  }
3908
3957
  },
@@ -4030,6 +4079,11 @@ var toPPOCRCommand = (0, import_core5.buildCommand)({
4030
4079
  brief: `Regex pattern to match Label Studio files (should match .json files). Default: "${DEFAULT_LABEL_STUDIO_FILE_PATTERN}"`,
4031
4080
  parse: String,
4032
4081
  optional: true
4082
+ },
4083
+ generateFileState: {
4084
+ kind: "boolean",
4085
+ brief: "Generate a file state file for each input directory",
4086
+ optional: true
4033
4087
  }
4034
4088
  }
4035
4089
  },