Skip to content

Util files needed #4

@zfogg

Description

@zfogg

Recommended Utilities (by priority)

  1. ImageCache.h - Async Image Loading (HIGH PRIORITY)

Problem: 6+ components duplicate avatar loading/scaling logic
// Current: Each component manually loads, scales, clips to circle
if (avatarImage.isValid()) {
auto scaledImage = avatarImage.rescaled(bounds.getWidth(), bounds.getHeight()...);
// clip to circle, draw...
}

Solution:
// ImageCache with LRU eviction, async loading, placeholder support
ImageCache::loadAsync(url, [this](juce::Image img) {
avatarImage = img;
repaint();
});

// Helper for circular avatars
ImageCache::drawCircularAvatar(g, bounds, image, placeholder);


  1. Json.h - JSON Helpers (HIGH PRIORITY)

Problem: 354 instances of verbose juce::var property access
// Current: Verbose and error-prone
auto val = json.getProperty("user", juce::var()).getProperty("name", "").toString();
int count = static_cast(json.getProperty("count", 0));

Solution:
namespace Json {
juce::String getString(const juce::var& json, const char* key, const juce::String& defaultVal = {});
int getInt(const juce::var& json, const char* key, int defaultVal = 0);
bool getBool(const juce::var& json, const char* key, bool defaultVal = false);
float getFloat(const juce::var& json, const char* key, float defaultVal = 0.0f);
juce::var getObject(const juce::var& json, const char* key);
juce::var getArray(const juce::var& json, const char* key);

  // Nested access: Json::getString(json, "user.profile.name")
  juce::String getNestedString(const juce::var& json, const char* path);

}


  1. Async.h - Threading Helpers (MEDIUM PRIORITY)

Problem: 164 threading patterns, many doing similar things
// Current: Manual thread management
std::thread(this, url {
auto result = fetchData(url);
juce::MessageManager::callAsync(this, result {
handleResult(result);
});
}).detach();

Solution:
namespace Async {
// Run on background thread, callback on message thread
template
void run(std::function<T()> work, std::function<void(T)> onComplete);

  // Debounce rapid calls (for search input)
  void debounce(const juce::String& key, int delayMs, std::function<void()> action);

  // Simple delay
  void delay(int ms, std::function<void()> action);

}


  1. Result.h - Error Handling (MEDIUM PRIORITY)

Problem: Inconsistent error handling with bool + string pairs
// Current: Ad-hoc error passing
void callback(bool success, const juce::var& data); // What's the error?

Solution:
template
class Result {
public:
static Result ok(T value);
static Result error(const juce::String& message);

  bool isOk() const;
  bool isError() const;
  T getValue() const;
  juce::String getError() const;

  // Monadic operations
  template<typename U>
  Result<U> map(std::function<U(T)> fn);

};

// Usage
Result result = api.fetchProfile(userId);
if (result.isOk())
setProfile(result.getValue());
else
Log::error(result.getError());


  1. Validate.h - Input Validation (LOW PRIORITY)

Problem: 177 string empty checks, scattered validation logic
namespace Validate {
bool isEmail(const juce::String& str);
bool isUrl(const juce::String& str);
bool isUsername(const juce::String& str); // alphanumeric, 3-20 chars
bool inRange(int val, int min, int max);

  // Sanitization
  juce::String sanitizeUsername(const juce::String& input);
  juce::String escapeHtml(const juce::String& input);

}


  1. UIHelpers.h - Drawing Utilities (LOW PRIORITY)

Problem: 70 rounded rectangle draws with similar patterns
namespace UI {
void drawCard(juce::Graphics& g, juce::Rectangle bounds,
juce::Colour bg, float cornerRadius = 8.0f);

  void drawBadge(juce::Graphics& g, juce::Rectangle<int> bounds,
                 const juce::String& text, juce::Colour bg, juce::Colour fg);

  void drawAvatar(juce::Graphics& g, juce::Rectangle<int> bounds,
                  const juce::Image& image, const juce::String& initials);

  // Truncate text with ellipsis
  juce::String truncate(const juce::String& text, const juce::Font& font, int maxWidth);

}


  1. Constants.h - Magic Numbers (LOW PRIORITY)

namespace Constants {
// API
constexpr int API_TIMEOUT_MS = 30000;
constexpr int MAX_UPLOAD_SIZE_MB = 50;

  // Audio
  constexpr int MAX_RECORDING_SECONDS = 60;
  constexpr int DEFAULT_BPM = 120;
  constexpr float TARGET_LUFS = -14.0f;

  // UI
  constexpr int POST_CARD_HEIGHT = 120;
  constexpr int AVATAR_SIZE = 40;
  constexpr float CORNER_RADIUS = 8.0f;

  // Cache
  constexpr int IMAGE_CACHE_SIZE = 50;
  constexpr int AUDIO_CACHE_SIZE = 10;

}


Summary Table

Utility Lines Saved Complexity Priority
ImageCache.h ~200 Medium HIGH
Json.h ~300 Low HIGH
Async.h ~150 Medium MEDIUM
Result.h ~100 Low MEDIUM
Validate.h ~50 Low LOW
UIHelpers.h ~100 Low LOW
Constants.h ~50 Trivial LOW

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions