取り組みの背景
モダンなアプリケーション開発において、高品質なサウンドデザインは差別化の大きな要素です。しかし、プロフェッショナルな音楽やサウンド効果を制作するには、通常、音響エンジニアや作曲家に依頼する必要があり、時間とコストがかかります。
Suno AI は、テキストからリアルな音楽を自動生成するAIサービスであり、Antigravity と組み合わせることで、開発フローを大幅に効率化できます。ここでSuno AI と Antigravity の連携方法から、実際のアプリケーション実装まで、ステップバイステップで解説します。
Suno AI とは
概要と特徴
Suno AI は、テキストプロンプトから高品質な音楽を自動生成するAIプラットフォームです。以下の特徴があります:
- テキストから楽曲生成: 説明的なプロンプトから、完全な楽曲を作成
- 複数のジャンル対応: ロック、ポップ、クラシック、アンビエント、EDM など多彩なスタイル
- カスタマイズ性: 楽器、テンポ、ボーカルスタイルなどを細かく指定可能
- API 対応: プログラマティックなアクセスが可能
Antigravity との相性
Antigravity のAIアシスタント機能を活用することで、以下が実現できます:
- Suno AI へのプロンプトを、自然言語から自動生成
- 複数の楽曲を一括生成する際のワークフロー自動化
- 生成された音楽メタデータの整理と管理
- API統合のコード生成
Suno AI との連携準備
アカウント設定
# 1. Suno AI にサインアップ
# https://www.suno.ai に訪問し、アカウントを作成
# 2. API キーを取得
# Dashboard > Settings > API Keys から、API キーをコピー
# 3. 環境変数に設定
export SUNO_API_KEY="your_api_key_here"Antigravity での設定
Antigravity で Suno AI を活用するには、プロンプトをうまく設計することが重要です:
あなたは音楽生成の専門家です。
ユーザーが希望するアプリケーション用の BGM を生成します。
要件:
- ジャンル、テンポ、気分を明確に指定
- サンプリングレート、長さなどの仕様を含める
- ライセンスの制限を確認する
BGM 生成のベストプラクティス
ゲームアプリ向け BGM
ゲーム「エスケープアドベンチャー」用の BGM を生成してください。
仕様:
- ジャンル: 冒険的なアンビエント
- テンポ: 120 BPM
- 長さ: 3 分間のループ可能な楽曲
- 楽器: シンセサイザー、パーカッション
- ボーカル: なし
- 雰囲気: 神秘的で興奮度の高い
プロンプト例:
"Epic adventure ambient track with mysterious synth layers,
tribal percussion elements, building tension, 120 BPM,
loopable 3-minute composition"モバイルアプリ向けループBGM
// 生成リクエスト例
const bgmRequest = {
prompt: "Calm, minimalist ambient background music suitable for focus/productivity apps. Soft piano with subtle string pads. 60 BPM, 2-minute loop",
model: "chirp-v3",
duration: 120,
loop: true
};
// Suno API を呼び出し
async function generateBGM(request) {
const response = await fetch('https://api.suno.ai/v1/generate', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.SUNO_API_KEY}`,
'Content-Type': 'application/json'
},
body: JSON.stringify(request)
});
return response.json();
}効果音(SFX)の生成
効果音プロンプトの設計
効果音は、より短く、シンプルなプロンプトで最良の結果が得られます:
生成対象: ボタンクリック音
- タイプ: デジタルピング
- 長さ: 0.5 秒
- 周波数: 明るく、高音
プロンプト例:
"Bright digital ping sound effect for UI button click, 500ms duration, high frequency, crisp and clear"アプリ内での SFX 統合例
class SoundEffectManager {
constructor() {
this.sfxLibrary = {};
}
async generateSFX(sfxType, prompt) {
const response = await fetch('https://api.suno.ai/v1/generate', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.SUNO_API_KEY}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({
prompt: prompt,
duration: 2, // 最大2秒の効果音
model: 'chirp-v3'
})
});
const result = await response.json();
this.sfxLibrary[sfxType] = result.audio_url;
return result;
}
playSFX(sfxType) {
const audio = new Audio(this.sfxLibrary[sfxType]);
audio.play();
}
}
// 使用例
const soundManager = new SoundEffectManager();
await soundManager.generateSFX('buttonClick', 'Quick digital beep for button click');
soundManager.playSFX('buttonClick');API 統用とワークフロー自動化
Antigravity で複数曲の一括生成
// Antigravity プロンプト例
const prompt = `
I need to generate a complete audio package for a mobile game.
Generate prompts for the following:
1. Main Menu BGM - Uplifting, 3 minutes, suitable for menu
2. Level Background - Ambient, loopable, 2 minutes
3. Victory Sound - Short, celebratory, 2 seconds
4. Game Over Sound - Dramatic, 3 seconds
5. Coin Pickup - Digital jingle, 0.5 seconds
Format as JSON with fields: name, prompt, duration, type
`;
// 生成されたプロンプト JSON を Suno API で順次処理
async function generateAudioPackage(generatedPrompts) {
const results = [];
for (const item of generatedPrompts) {
const response = await generateWithSunoAPI(item.prompt, item.duration);
results.push({
name: item.name,
type: item.type,
audioUrl: response.audio_url,
duration: item.duration
});
// API レート制限に対応
await new Promise(resolve => setTimeout(resolve, 1000));
}
return results;
}生成結果の管理とメタデータ保存
class AudioAssetManager {
async saveAudioMetadata(audioData) {
const metadata = {
id: crypto.randomUUID(),
name: audioData.name,
type: audioData.type,
duration: audioData.duration,
url: audioData.audioUrl,
createdAt: new Date().toISOString(),
license: 'commercial-use-allowed',
format: 'mp3',
sampleRate: 48000
};
// データベースに保存
await db.audioAssets.insert(metadata);
return metadata;
}
async exportAudioPackage(projectId) {
const assets = await db.audioAssets.find({ projectId });
return {
project: projectId,
audioAssets: assets,
totalDuration: assets.reduce((sum, a) => sum + a.duration, 0),
exportedAt: new Date().toISOString()
};
}
}ライセンスと法的考慮事項
Suno AI の利用規約
- 商用利用: Suno の利用規約によると、生成された音楽の商用利用には明確なライセンスが必要
- クレジット表記: アプリ内でのクレジット表記ポリシーを確認
- 著作権: 生成音楽の著作権帰属を明確にする
アプリへの組み込み時のチェックリスト
## ライセンス確認チェック
- [ ] Suno AI 規約で商用利用が許可されている
- [ ] アプリケーション内でSuno AIへのクレジット表記が必要かどうか確認
- [ ] 著作権情報をメタデータに記録
- [ ] ユーザー向けドキュメントに利用条件を記載
- [ ] 定期的なライセンス更新スケジュールを確立Web アプリケーションでの実装例
React での統合
import { useEffect, useState } from 'react';
function AudioPlayer({ trackType }) {
const [audioUrl, setAudioUrl] = useState(null);
const [isLoading, setIsLoading] = useState(false);
const generateAudio = async () => {
setIsLoading(true);
// Antigravity API を通じてプロンプトを生成
const promptResponse = await fetch('/api/generate-audio-prompt', {
method: 'POST',
body: JSON.stringify({ trackType })
});
const { prompt } = await promptResponse.json();
// Suno API で音楽を生成
const sunoResponse = await fetch('/api/suno-generate', {
method: 'POST',
body: JSON.stringify({ prompt })
});
const { audio_url } = await sunoResponse.json();
setAudioUrl(audio_url);
setIsLoading(false);
};
return (
<div className="audio-player">
<button onClick={generateAudio} disabled={isLoading}>
{isLoading ? 'Generating...' : 'Generate Audio'}
</button>
{audioUrl && (
<audio controls>
<source src={audioUrl} type="audio/mpeg" />
</audio>
)}
</div>
);
}バックエンド API の実装
// api/suno-generate.js
export async function POST(req) {
const { prompt } = await req.json();
try {
const response = await fetch('https://api.suno.ai/v1/generate', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.SUNO_API_KEY}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({
prompt: prompt,
model: 'chirp-v3'
})
});
const data = await response.json();
return new Response(JSON.stringify(data), {
status: 200,
headers: { 'Content-Type': 'application/json' }
});
} catch (error) {
return new Response(JSON.stringify({ error: error.message }), {
status: 500
});
}
}モバイルアプリケーションでの実装例
iOS (SwiftUI)
import AVFoundation
class AudioManager: NSObject, ObservableObject {
@Published var isPlaying = false
@Published var currentTrack: String?
private var audioPlayer: AVAudioPlayer?
func playAudio(from url: URL) {
do {
audioPlayer = try AVAudioPlayer(contentsOf: url)
audioPlayer?.play()
isPlaying = true
} catch {
print("Failed to play audio: \(error)")
}
}
func generateAndPlayBGM(trackType: String) async {
// Antigravity API を呼び出してプロンプト生成
let promptRequest = URLRequest(url: URL(string: "https://api.antigravity.app/generate-audio-prompt")!)
// Suno API を呼び出して音楽生成
// 結果を再生
}
}
struct AudioPlayerView: View {
@StateObject var audioManager = AudioManager()
var body: some View {
VStack {
Button(action: {
Task {
await audioManager.generateAndPlayBGM(trackType: "menu-bgm")
}
}) {
Text("Play BGM")
}
Text(audioManager.isPlaying ? "Playing..." : "Paused")
}
}
}Android (Kotlin)
import android.media.MediaPlayer
class AudioManager {
private var mediaPlayer: MediaPlayer? = null
suspend fun generateAndPlayBGM(trackType: String) {
try {
// Suno API から音声を取得
val audioUrl = fetchSunoGeneratedAudio(trackType)
mediaPlayer = MediaPlayer().apply {
setDataSource(audioUrl)
prepareAsync()
setOnPreparedListener { mp ->
mp.start()
}
}
} catch (e: Exception) {
e.printStackTrace()
}
}
private suspend fun fetchSunoGeneratedAudio(trackType: String): String {
// Suno API 呼び出し処理
return "audio_url"
}
fun stop() {
mediaPlayer?.stop()
mediaPlayer?.release()
mediaPlayer = null
}
}トラブルシューティングと最適化
よくある問題と解決策
1. API のレート制限
class RateLimitedSunoClient {
constructor(maxRequestsPerMinute = 10) {
this.maxRequests = maxRequestsPerMinute;
this.requestTimestamps = [];
}
async generateWithRateLimit(prompt) {
const now = Date.now();
const oneMinuteAgo = now - 60000;
// 1分以内のリクエスト数を数える
this.requestTimestamps = this.requestTimestamps.filter(
ts => ts > oneMinuteAgo
);
if (this.requestTimestamps.length >= this.maxRequests) {
const waitTime = 60000 - (now - this.requestTimestamps[0]);
await new Promise(resolve => setTimeout(resolve, waitTime));
}
this.requestTimestamps.push(now);
return await this.generateAudio(prompt);
}
}2. 音声品質の最適化
- フォーマット: MP3 (128-320 kbps) または WAV を使用
- サンプリングレート: 44.1 kHz または 48 kHz を推奨
- ビット深度: 16-bit 以上を使用
3. 生成時間の短縮
// バッチ処理で複数曲を並列生成
async function generateAudioBatch(prompts) {
const promises = prompts.map(prompt =>
generateWithSunoAPI(prompt)
);
return Promise.all(promises);
}まとめ
Suno AI と Antigravity の組み合わせは、アプリケーション開発における音声デザインの生産性を大幅に向上させます:
- 迅速な開発: プロンプトから数秒で高品質な音楽を生成
- カスタマイズ性: テキストベースのコントロールで細かい調整が可能
- コスト削減: 専門家に依頼する必要がなく、コストを大幅に削減
- スケーラビリティ: API 統合により、複数プロジェクトでの運用が簡単
適切なプロンプト設計、ライセンス管理、API の最適化により、あなたのアプリケーションに独自の音声体験を簡単に追加できます。