Spela ljud i Objective-C

Tråden skapades och har fått 14 svar. Det senaste inlägget skrevs .
1

Hur spelar man ljud i Objective C?

Försökte sätta in följande i en action:

Citat:

NSSound *asound = [NSSound soundNamed:@asound];

if (loaded && ![asound isPlaying])
{
[asound play];
}

men får felmeddelandet: "error: 'loaded' undeclared (first use of this function)"

Vad gör jag för fel?

En annan sak också.. Det här är säkert extremt enkelt, men jag hittar det inte nånstans. Jag har skapat ett program med ett namn, men nu vill jag byta namn på programmet. Hur gör jag det?

O

  • Medlem
  • Stockholm
  • 2007-11-03 08:22

Om det är all kod du skrivit, har du nog inte förstått NSSound riktigt. Kika på http://developer.apple.com/documentation/Cocoa/Reference/ApplicationKit/Classes/NSSound_Class/index.html#//apple_ref/doc/uid/TP40004112!

Vänligen, Ylan

Ursprungligen av olindh:

En annan sak också.. Det här är säkert extremt enkelt, men jag hittar det inte nånstans. Jag har skapat ett program med ett namn, men nu vill jag byta namn på programmet. Hur gör jag det?

Nu förutsätter jag att du arbetar i Xcode. Då visar du info för ditt target. Under Build söker du efter en inställning som heter "Product Name". Ändra den till det namn du vill använda.

Därefter måste du köra en clean all från Build-menyn. Annars kommer det gamla namnet att finnas kvar. När du gjort det och gör ett bygge kommer programmet ha det nya namnet.

Du får det felmeddelandet därför att du inte talat om vad loaded är för variabel. Gör så här istället:

NSSound *asound = [NSSound soundNamed:@asound]; 

if (![asound isPlaying]) 
{ 
    [asound play]; 
}
  • Medlem
  • Stockholm
  • 2007-11-04 08:09
Ursprungligen av Marcus K:

Du får det felmeddelandet därför att du inte talat om vad loaded är för variabel. Gör så här istället:

NSSound *asound = [NSSound soundNamed:@asound]; 

if (![asound isPlaying]) 
{ 
    [asound play]; 
}

Hej Marcus,

Blir detta en minnesläcka i pre-Leopard version?

Jag testade detta:

- (IBAction)playSound:(id)sender {
	if (![mySound isPlaying]){
		  [mySound play];
		  }
}
		  
- (void) awakeFromNib{
	mySound = [NSSound soundNamed:@Submarine];
}

Vilket fungerar utmärkt (med mySound som instansvariabel), jag kan klicka på min, till -playSound kopplade knapp många gånger utan problem. Tänker jag rätt om jag tolkar det som mySound aldrig blir släppt?

Det jag undrar är huruvida -soundNamed skapar en nytt objekt varje gång. I så fall torde din rutin läcka mySound Hur i helsike kan Garbage Collection egentligen fungera?

Vänligen, Ylan, som äntligen börjat knacka litet igen

Senast redigerat 2007-11-04 08:22

Marcus, you're a god. Tack!
Och tack Yvan, jag ska ta en titt på länken!

Du kommer att använda samma instans varje gång du kör soundNamed. Så vida du inte implicit allokerar en egen instans eller kopierar en befintlig borde det inte läcka minne att köra soundNamed flera gånger.

  • Medlem
  • Stockholm
  • 2007-11-04 08:36
Ursprungligen av Marcus K:

Du kommer att använda samma instans varje gång du kör soundNamed. Så vida du inte implicit allokerar en egen instans eller kopierar en befintlig borde det inte läcka minne att köra soundNamed flera gånger.

Tack, från en tidig söndagskodare. Skall jag tolka det som att -soundNamed testar huruvida den behöver allokera minne, och om den inte behöver det inte gör det?

Vänligen, Ylan

Såvitt jag förstår ja.

Men nu passade jag på att kontrollera. En gång i sekunden körde +soundNamed och därefter -play för att spela upp Submarine. Enligt Instruments användes bara en instans och minnesåtgången för den höll konstant nivå. Så det ser ut att stämma.

Angående Garbage Collection har Apple skrivit en guide på ADC. Jag har själv inte läst den helt och hållet men den förklarar principerna för hur det fungerar.
http://developer.apple.com/documentation/Cocoa/Conceptual/GarbageCollection/index.html

Det där läcker inte minne, däremot kan du får problem med att mySound releasas för tidigt, eftersom +soundNamed: bör returnera en autoreleasad instans av NSSound. Således måste du retaina den om du ska lägga den i en ivar.

  • Medlem
  • Stockholm
  • 2007-11-04 12:19
Ursprungligen av DrRotmos:

Det där läcker inte minne, däremot kan du får problem med att mySound releasas för tidigt, eftersom +soundNamed: bör returnera en autoreleasad instans av NSSound. Således måste du retaina den om du ska lägga den i en ivar.

Men torde den inte releasas direkt efter att -awakeFromNib körts? Jag har inte haft några problem med min kod ovan. Jag kopplade en knapp till -playSound

Vänligen, Ylan

+soundNamed: returnerar objekt från en intern lista av ljud, precis som NSFonts +fontWithName:size: gör, vilket gör att det råkar funka eftersom NSSound själv retainar objekten. Dock är det här absolut inget man ska lita på, så protokollen för objektägarskap gäller: du är skyldig att retaina NSSound-instansen om du vill behålla den utanför det omedelbara scopet.

  • Medlem
  • Simrishamn
  • 2007-11-09 13:41

Precis, det är snarare ett optimeringstilltag från AppKit's sida att låta ljudet leva vidare. Det vore ju ineffektivt att ladda in en ljudfil från skiva varje gång det ska spelas upp.

Dokumentationen antyder att instansen av NSSound finns redan.

-Returns the NSSound instance associated with name.-

1
Bevaka tråden