Files
rfcp/RFCP-Fixes-Iteration1.md

6.2 KiB

RFCP Fixes - Iteration 1

Issues to Fix:

1. Heatmap Colors - More Obvious Gradient

Current problem: Green→Yellow→Red gradient not obvious enough

Fix: Update src/components/map/Heatmap.tsx

Change the gradient to use more distinct colors with better visibility:

// In Heatmap.tsx, update the gradient prop:

<HeatmapLayer
  points={heatmapPoints}
  longitudeExtractor={(p: any) => p[1]}
  latitudeExtractor={(p: any) => p[0]}
  intensityExtractor={(p: any) => p[2]}
  gradient={{
    0.0: '#0000ff',  // Blue (very weak, -120 dBm)
    0.2: '#00ffff',  // Cyan (weak, -110 dBm)
    0.4: '#00ff00',  // Green (fair, -100 dBm)
    0.6: '#ffff00',  // Yellow (good, -85 dBm)
    0.8: '#ff7f00',  // Orange (strong, -70 dBm)
    1.0: '#ff0000',  // Red (excellent, > -70 dBm)
  }}
  radius={25}
  blur={15}
  max={1.0}
/>

Reasoning:

  • Blue/Cyan for weak signals (more intuitive - "cold" = weak)
  • Green for acceptable
  • Yellow/Orange for good
  • Red for excellent (hot = strong)

This is actually inverted from typical "green=good", but in RF planning, RED = STRONG SIGNAL = GOOD!


2. Coverage Radius - Increase to 100km

Current problem: Max radius only 20km, not enough for tactical planning

Fix: Update src/components/panels/SiteForm.tsx (or wherever Coverage Settings are)

Find the radius slider and change:

// Old:
<Slider
  label="Radius (km)"
  min={1}
  max={20}  // ← Change this
  step={1}
  value={coverageSettings.radius}
  onChange={(value) => updateCoverageSettings({ radius: value })}
/>

// New:
<Slider
  label="Radius (km)"
  min={1}
  max={100}  // ← Increased to 100km
  step={5}   // ← Larger step for easier control
  value={coverageSettings.radius}
  onChange={(value) => updateCoverageSettings({ radius: value })}
  help="Calculation area around each site"
/>

Also update default value in store:

// In src/store/coverage.ts or wherever coverage settings are initialized:
const initialSettings = {
  radius: 10,        // Default 10km (reasonable starting point)
  resolution: 200,   // 200m resolution
  rsrpThreshold: -120
};

3. Save & Calculate Button

Current problem: Two separate buttons, extra click needed

Fix: Update src/components/panels/SiteForm.tsx

Replace the button section:

// Old:
<div className="flex gap-2">
  <Button onClick={handleSave}>Save</Button>
  <Button onClick={handleDelete} variant="danger">Delete</Button>
</div>

// New:
<div className="flex gap-2">
  <Button 
    onClick={handleSaveAndCalculate}
    variant="primary"
    className="flex-1"
  >
    💾 Save & Calculate Coverage
  </Button>
  <Button 
    onClick={handleSave}
    variant="secondary"
    className="flex-1"
  >
    💾 Save Only
  </Button>
  <Button 
    onClick={handleDelete} 
    variant="danger"
  >
    🗑️ Delete
  </Button>
</div>

// Add the handler:
const handleSaveAndCalculate = async () => {
  // Save the site first
  await handleSave();
  
  // Then trigger coverage calculation
  const sites = useSitesStore.getState().sites;
  const coverage = useCoverageStore.getState();
  
  // Calculate coverage for all sites
  await coverage.calculateCoverage(sites);
  
  // Show success toast
  toast.success('Site saved and coverage calculated!');
};

Alternative (simpler): Just make the main button do both:

<div className="flex gap-2">
  <Button 
    onClick={async () => {
      await handleSave();
      // Auto-trigger calculate after save
      const sites = useSitesStore.getState().sites;
      await useCoverageStore.getState().calculateCoverage(sites);
    }}
    variant="primary"
    className="flex-1"
  >
    💾 Save & Calculate
  </Button>
  <Button 
    onClick={handleDelete} 
    variant="danger"
  >
    🗑️ Delete
  </Button>
</div>

4. Legend Colors Update

Fix: Update src/components/map/Legend.tsx to match new gradient:

const signalRanges = [
  { label: 'Excellent', range: '> -70 dBm', color: '#ff0000' },    // Red
  { label: 'Good', range: '-70 to -85 dBm', color: '#ff7f00' },    // Orange
  { label: 'Fair', range: '-85 to -100 dBm', color: '#ffff00' },   // Yellow
  { label: 'Poor', range: '-100 to -110 dBm', color: '#00ff00' },  // Green
  { label: 'Weak', range: '-110 to -120 dBm', color: '#00ffff' },  // Cyan
  { label: 'Very Weak', range: '< -120 dBm', color: '#0000ff' },   // Blue
];

5. Resolution Adjustment for Large Radius

Problem: 200m resolution + 100km radius = MANY points = slow calculation

Fix: Auto-adjust resolution based on radius:

// In src/store/coverage.ts or coverage calculator:

const getOptimalResolution = (radius: number): number => {
  if (radius <= 10) return 100;   // 100m for small areas
  if (radius <= 30) return 200;   // 200m for medium areas
  if (radius <= 60) return 300;   // 300m for large areas
  return 500;                     // 500m for very large areas (100km)
};

// Use in calculation:
const resolution = settings.resolution || getOptimalResolution(settings.radius);

Or add a notice in UI:

<p className="text-sm text-gray-500">
  💡 Larger radius = longer calculation time. 
  Consider increasing resolution (200m  500m) for faster results.
</p>

Summary of Changes:

  1. Heatmap gradient: Blue → Cyan → Green → Yellow → Orange → Red
  2. Max radius: 20km → 100km (step: 5km)
  3. Button: "Save & Calculate" as primary action
  4. Legend: Updated colors to match new gradient
  5. Performance: Auto-adjust resolution or show warning

Implementation Order:

  1. Start with colors (easiest, biggest visual impact)
  2. Then radius (simple slider change)
  3. Then button (requires store integration)
  4. Test everything

Files to Edit:

frontend/src/components/map/Heatmap.tsx       - gradient colors
frontend/src/components/map/Legend.tsx        - legend colors
frontend/src/components/panels/SiteForm.tsx   - radius slider + button
frontend/src/store/coverage.ts                - default settings

Would you like me to create the exact code patches for Claude Code to apply? Or should I create complete replacement files?