Skip to content

Latest commit

 

History

History
244 lines (191 loc) · 7.16 KB

File metadata and controls

244 lines (191 loc) · 7.16 KB

Phase 1 Migration Complete: Simple @Input Properties to Signals

Summary

Successfully migrated 89 out of 105 @Input properties (85%) in the ngx-extended-pdf-viewer.component.ts file from Angular decorators to the new signals API.

What Was Done

Migrated (89 properties)

  • All simple @Input() properties without custom setters/getters
  • Properties with default values, type annotations, and complex expressions
  • Properties marked as required with ! (definite assignment assertion)

Examples of Migration Patterns

Pattern 1: Optional with no default

// Before
@Input()
public customFindbarInputArea: TemplateRef<any> | undefined;

// After
public customFindbarInputArea = input<TemplateRef<any>>();

Pattern 2: With default value and type

// Before
@Input()
public showTextEditor: ResponsiveVisibility = 'xxl';

// After
public showTextEditor = input<ResponsiveVisibility>('xxl');

Pattern 3: Simple boolean

// Before
@Input()
public enableDragAndDrop = true;

// After
public enableDragAndDrop = input(true);

Pattern 4: Complex default expression

// Before
@Input()
public showCommentEditor: ResponsiveVisibility = pdfDefaultOptions.enableComment ? 'xxl' : false;

// After
public showCommentEditor = input<ResponsiveVisibility>(pdfDefaultOptions.enableComment ? 'xxl' : false);

Pattern 5: Required input

// Before
@Input()
public rotation!: 0 | 90 | 180 | 270;

// After
public rotation = input.required<0 | 90 | 180 | 270>();

What Was NOT Done (For Later Phases)

Phase 2: @Input Setters (16 properties)

Properties with custom setter logic that need to be converted to effect():

  1. formData - Updates form support service
  2. pageViewMode - Complex view mode handling with redraw
  3. scrollMode - Syncs with PDF viewer application
  4. enablePrintAutoRotate - Updates PDF viewer settings
  5. minifiedJSLibraries - Modifies pdfDefaultOptions
  6. src - Async blob/URL processing
  7. base64Src - Base64 decoding and loading
  8. height - Manages minHeight and autoHeight
  9. showSidebarButton - Responsive visibility with storage
  10. sidebarVisible - Emits change events
  11. showRotateButton - Sets both CW and CCW buttons
  12. handTool - iOS-specific handling
  13. showScrollingButtons - Sets 6 related properties
  14. page - Number/string conversion
  15. zoomLevels - Array manipulation
  16. mobileFriendlyZoom - Complex zoom calculation

Phase 3: @Output (37 properties)

Event emitters to be converted to output():

  • annotationEditorEvent
  • srcChange
  • pageViewModeChange
  • progress
  • scrollModeChange
  • currentZoomFactor
  • rotationChange
  • And 30 more...

Phase 4: @ViewChild (5 properties)

View child queries to be converted to viewChild():

  • dummyComponents
  • root
  • secondaryToolbarComponent
  • dynamicCSSComponent
  • sidebarComponent

Known Issues (Expected)

The component will not compile after Phase 1. This is intentional and expected.

Compilation Errors

  1. Setter assignment errors: Setters try to assign to readonly signals

    // Error: Cannot assign to showRotateCwButton because it's an InputSignal
    public set showRotateButton(visibility: ResponsiveVisibility) {
      this.showRotateCwButton = visibility;  // ← Error here
      this.showRotateCcwButton = visibility; // ← And here
    }
  2. Interface compatibility errors:

    // NgxHasHeight interface expects: minHeight: string
    // Component now has: minHeight: InputSignal<string | undefined>
  3. Property access errors: Code that reads these properties needs to call them as functions

    // Old way
    if (this.showBorders) { }
    
    // New way (will be fixed in Phase 2)
    if (this.showBorders()) { }

Why This Is OK

These errors will be systematically fixed in Phase 2 when:

  • Setters are converted to effect()
  • Property reads are updated to use the signal getter ()
  • Interfaces are updated to accept signals

File Changes

Modified

  • /workspace/ngx-extended-pdf-viewer/projects/ngx-extended-pdf-viewer/src/lib/ngx-extended-pdf-viewer.component.ts
    • Line 11: Added input to imports
    • 89 properties converted from @Input() decorator to input() signal

Created

  • ngx-extended-pdf-viewer.component.ts.backup - Original file backup
  • MIGRATION-PHASE-1-SUMMARY.md - Detailed summary with examples
  • MIGRATED-PROPERTIES-PHASE-1.md - Complete list of all 89 properties
  • PHASE-1-COMPLETE.md - This file

Statistics

Metric Count
Total decorators in file 147
@Input decorators before 105
@Input decorators migrated 89
@Input decorators remaining 16
@Output decorators 37
@ViewChild decorators 5
Lines in file 2,701
Migration success rate 85% of @Input

Verification

Run these commands to verify the migration:

# Count migrated input signals
grep -E "public \w+ = input" ngx-extended-pdf-viewer.component.ts | wc -l
# Expected: 89

# Count remaining @Input decorators
grep -c "^\s*@Input()" ngx-extended-pdf-viewer.component.ts
# Expected: 16

# Count @Output decorators
grep -c "^\s*@Output()" ngx-extended-pdf-viewer.component.ts
# Expected: 37

# Count @ViewChild decorators
grep -c "^\s*@ViewChild" ngx-extended-pdf-viewer.component.ts
# Expected: 5

Next Steps

Immediate (Phase 2a): Fix Setter Properties

Convert @Input setters to input() + effect() pattern:

  1. Replace @Input() set property(value) with public property = input<Type>(default)
  2. Create effect() to handle the setter logic
  3. Update any direct assignments to use .set() method

Immediate (Phase 2b): Migrate @Output

Convert @Output to output():

  1. Replace @Output() public event = new EventEmitter<Type>() with public event = output<Type>()
  2. Update emit() calls (no changes needed, API compatible)

Follow-up (Phase 3): Migrate @ViewChild

Convert @ViewChild to viewChild():

  1. Replace @ViewChild(Component) prop!: Component with public prop = viewChild.required<Component>()
  2. Update property access to use () for signal reading

Final (Phase 4): Cleanup

  1. Remove unused decorator imports (Input, Output, ViewChild)
  2. Update ngOnChanges if it references migrated properties
  3. Run full test suite
  4. Update component documentation

Migration Script

The migration was performed using a Python script that:

  1. Identified all @Input() decorators
  2. Checked if the next line had a setter (skip if yes)
  3. Parsed the property declaration (name, type, default value)
  4. Generated the equivalent input() signal declaration
  5. Updated the file in-place with proper formatting

Script location: /tmp/migrate_component.py

Rollback

If needed, restore the original file:

cp projects/ngx-extended-pdf-viewer/src/lib/ngx-extended-pdf-viewer.component.ts.backup \
   projects/ngx-extended-pdf-viewer/src/lib/ngx-extended-pdf-viewer.component.ts

Phase 1 Status: ✅ COMPLETE Phase 2 Status: ⏳ PENDING Phase 3 Status: ⏳ PENDING Phase 4 Status: ⏳ PENDING

Date: 2025-12-25 Component: ngx-extended-pdf-viewer.component.ts Total Properties Migrated: 89 / 147 (61%)