implemented audio formats conversion.

This commit is contained in:
morkt 2015-05-14 15:58:16 +04:00
parent 77f05a1b6b
commit 14ef2f9071
15 changed files with 254 additions and 55 deletions

View File

@ -79,6 +79,12 @@
<setting name="appLastImageFormat" serializeAs="String">
<value>PNG</value>
</setting>
<setting name="appConvertAudio" serializeAs="String">
<value>False</value>
</setting>
<setting name="appExtractAudio" serializeAs="String">
<value>True</value>
</setting>
</GARbro.GUI.Properties.Settings>
</userSettings>
</configuration>

View File

@ -4,33 +4,54 @@
xmlns:s="clr-namespace:GARbro.GUI.Strings"
xmlns:p="clr-namespace:GARbro.GUI.Properties"
xmlns:local="clr-namespace:GARbro.GUI"
Title="{x:Static s:guiStrings.TextExtractTitle}" Height="200" Width="411.713"
Title="{x:Static s:guiStrings.TextExtractTitle}" Height="228" Width="411.713"
ShowInTaskbar="False" WindowStartupLocation="CenterOwner" ResizeMode="NoResize" Background="{DynamicResource {x:Static SystemColors.ControlBrushKey}}">
<!-- Binding to application settings causes Visual Studio designer to crash.
Replace {Settings} bindings with "True" for designer to work.
WPF is awesome. -->
<Grid Margin="0,0,0,0">
<Grid.RowDefinitions>
<RowDefinition Height="61*"/>
<RowDefinition Height="70*"/>
<RowDefinition Height="41*"/>
<RowDefinition Height="85*"/>
<RowDefinition Height="53*"/>
</Grid.RowDefinitions>
<TextBlock x:Name="ExtractLabel" Text="{x:Static s:guiStrings.LabelExtractAllTo}" Margin="10,10,10,0" VerticalAlignment="Top" Height="15"/>
<local:ExtAutoCompleteBox x:Name="DestinationDir" Margin="10,0,41,9" VerticalAlignment="Bottom"
Text="{Binding RelativeSource={RelativeSource AncestorType={x:Type local:ExtractDialog}}, Path=Destination, Mode=TwoWay}"/>
<Button Margin="0,0,10,9" VerticalAlignment="Bottom" HorizontalAlignment="Right"
Command="{x:Static local:Commands.Browse}">
<TextBlock x:Name="ExtractLabel" Text="{x:Static s:guiStrings.LabelExtractAllTo}" Margin="10,10,9.87,0" VerticalAlignment="Top" Height="15"/>
<local:ExtAutoCompleteBox x:Name="DestinationDir" Margin="10,0,40.87,9.939" VerticalAlignment="Bottom"
Text="{Binding RelativeSource={RelativeSource AncestorType={x:Type local:ExtractDialog}}, Path=Destination, Mode=TwoWay}" Height="23"/>
<Button Margin="0,0,10,10" VerticalAlignment="Bottom" HorizontalAlignment="Right"
Command="{x:Static local:Commands.Browse}" Height="22" Width="22">
<Image Source="{StaticResource IconSearch}" Stretch="Uniform" UseLayoutRounding="True" SnapsToDevicePixels="True" Width="16" Height="16" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Button>
<CheckBox Name="ExtractImages" Content="{x:Static s:guiStrings.TextExtractImages}" HorizontalAlignment="Left" Margin="10,7.061,0,0" Grid.Row="1" VerticalAlignment="Top" Width="147" Height="15" IsChecked="True"/>
<Border BorderBrush="{x:Null}" Height="28" Width="115" Margin="0,0.061,127.87,0" Grid.Row="1" VerticalAlignment="Top" HorizontalAlignment="Right" >
<CheckBox Name="ExtractImages" Content="{x:Static s:guiStrings.TextExtractImages}" HorizontalAlignment="Left" Margin="10,6.061,0,0" Grid.Row="1" VerticalAlignment="Top" Width="147" Height="15"
IsChecked="{Binding Source={x:Static p:Settings.Default}, Path=appExtractImages, Mode=TwoWay}"/>
<!-- IsChecked="True"/> -->
<StackPanel Orientation="Horizontal" Grid.Row="1" Margin="0,0,10,0" HorizontalAlignment="Right">
<Border BorderBrush="{x:Null}" Height="28" Width="115" Grid.Row="1" VerticalAlignment="Top" HorizontalAlignment="Right" >
<TextBlock Text="{x:Static s:guiStrings.TextSaveImagesAs}" TextWrapping="Wrap" TextAlignment="Right" VerticalAlignment="Center" HorizontalAlignment="Right"/>
</Border>
<ComboBox Name="ImageConversionFormat" DisplayMemberPath="Tag" Margin="0,4.061,41.87,0" Grid.Row="1" VerticalAlignment="Top" Height="21" HorizontalAlignment="Right" Width="75">
</ComboBox>
<CheckBox x:Name="ExtractText" Content="{x:Static s:guiStrings.TextExtractText}" HorizontalAlignment="Left" Margin="10,35.061,0,0" Grid.Row="1" VerticalAlignment="Top" Width="120" Height="15" IsChecked="True"/>
<TextBlock Text="{x:Static s:guiStrings.TextEncoding}" Margin="0,35.061,128,0" TextAlignment="Right" VerticalAlignment="Top" Height="20" Grid.Row="1" HorizontalAlignment="Right" Width="109"/>
<ComboBox x:Name="TextEncoding" Margin="0,33.061,41.87,0" Grid.Row="1" VerticalAlignment="Top" Height="21" HorizontalAlignment="Right" Width="76">
</ComboBox>
<Button Content="{x:Static s:guiStrings.ButtonExtract}" Click="ExtractButton_Click" HorizontalAlignment="Right" Margin="0,0,103,10" Grid.Row="2" Width="75" Height="25" VerticalAlignment="Bottom" VerticalContentAlignment="Center" IsDefault="True"/>
<Button Content="{x:Static s:guiStrings.ButtonCancel}" Margin="0,0,10,10" Grid.Row="2" Height="25" VerticalAlignment="Bottom" VerticalContentAlignment="Center" IsCancel="True" HorizontalAlignment="Right" Width="75"/>
<ComboBox Name="ImageConversionFormat" DisplayMemberPath="Tag" Margin="10,3,0,0" VerticalAlignment="Top" Height="21" HorizontalAlignment="Right" Width="75"/>
</StackPanel>
<CheckBox x:Name="ExtractText" Content="{x:Static s:guiStrings.TextExtractText}" HorizontalAlignment="Left" Grid.Row="1" VerticalAlignment="Top"
Margin="10,34,0,0" Width="120" Height="15"
IsChecked="{Binding Source={x:Static p:Settings.Default}, Path=appExtractText, Mode=TwoWay}"/>
<!-- IsChecked="True"/> -->
<StackPanel Orientation="Horizontal" Grid.Row="1" Margin="0,34,10,0" HorizontalAlignment="Right">
<TextBlock Text="{x:Static s:guiStrings.TextEncoding}" TextAlignment="Right" VerticalAlignment="Top" Height="15" HorizontalAlignment="Right" Width="109"/>
<ComboBox x:Name="TextEncoding" VerticalAlignment="Top" Margin="10,0,0,0" Height="21" HorizontalAlignment="Right" Width="76"/>
</StackPanel>
<CheckBox x:Name="ExtractAudio" Content="{x:Static s:guiStrings.TextExtractAudio}" HorizontalAlignment="Left" Grid.Row="1" VerticalAlignment="Top"
Margin="10,62.061,0,0" Width="120" Height="15"
IsChecked="{Binding Source={x:Static p:Settings.Default}, Path=appExtractAudio, Mode=TwoWay}"/>
<!-- IsChecked="True"/> -->
<CheckBox x:Name="AudioConversion" Content="{x:Static s:guiStrings.TextConvertAudio}" Grid.Row="1"
Margin="0,62.061,10,0" Height="15" HorizontalAlignment="Right" ToolTip="{x:Static s:guiStrings.TooltipAudioFormats}" VerticalAlignment="Top"
IsEnabled="{Binding ElementName=ExtractAudio, Path=IsChecked}"
IsChecked="{Binding Source={x:Static p:Settings.Default}, Path=appConvertAudio, Mode=TwoWay}"/>
<!-- IsChecked="True"/> -->
<StackPanel Grid.Row="2" Orientation="Horizontal" Margin="0,0,10,15" HorizontalAlignment="Right" VerticalAlignment="Bottom" Height="25" Width="170">
<Button Content="{x:Static s:guiStrings.ButtonExtract}" Margin="0" Click="ExtractButton_Click" Grid.Row="2" Width="75" Height="25" VerticalAlignment="Bottom" IsDefault="True"/>
<Button Content="{x:Static s:guiStrings.ButtonCancel}" Margin="20,0,0,0" Height="25" VerticalAlignment="Bottom" IsCancel="True" Width="75"/>
</StackPanel>
</Grid>
<Window.CommandBindings>
<CommandBinding Command="{x:Static local:Commands.Browse}" Executed="BrowseExec" CanExecute="CanExecuteAlways"/>

View File

@ -1,6 +1,6 @@
// Game Resource Browser
//
// Copyright (C) 2014 by morkt
// Copyright (C) 2014-2015 by morkt
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
@ -49,8 +49,6 @@ namespace GARbro.GUI
Destination = destination;
DestinationDir.EnterKeyDown += acb_OnEnterKeyDown;
ExtractImages.IsChecked = Settings.Default.appExtractImages;
ExtractText.IsChecked = Settings.Default.appExtractText;
ExtractText.IsEnabled = false;
TextEncoding.IsEnabled = false;
@ -67,15 +65,7 @@ namespace GARbro.GUI
void ExtractButton_Click (object sender, RoutedEventArgs e)
{
this.DialogResult = true;
Settings.Default.appExtractImages = this.ExtractImages.IsChecked.Value;
Settings.Default.appExtractText = this.ExtractText.IsChecked.Value;
ExportImageFormat (ImageConversionFormat);
}
public ImageFormat GetImageFormat ()
{
var selected = ImageConversionFormat.SelectedItem as ImageFormatModel;
return null != selected ? selected.Source : null;
}
}
}

View File

@ -17,14 +17,20 @@
Command="{x:Static local:Commands.Browse}">
<Image Source="{StaticResource IconSearch}" Stretch="Uniform" UseLayoutRounding="True" SnapsToDevicePixels="True" Width="16" Height="16" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Button>
<StackPanel x:Name="ImageConversionOptions" Visibility="Visible" Orientation="Horizontal" Margin="10,60,0,0" Height="25" VerticalAlignment="Top" HorizontalAlignment="Left" Width="300">
<Grid Name="ConversionTypePanel" Margin="10,60,0,0" Height="25" Width="300" VerticalAlignment="Top" HorizontalAlignment="Left">
<StackPanel x:Name="ImageConversionOptions" Visibility="Visible" Orientation="Horizontal">
<TextBlock Text="{x:Static s:guiStrings.TextSaveAs}" Margin="0,0,7,0" TextWrapping="Wrap" TextAlignment="Right" VerticalAlignment="Center" HorizontalAlignment="Left"/>
<ComboBox x:Name="ImageConversionFormat" DisplayMemberPath="Tag" Margin="0" VerticalAlignment="Center" Height="21" Width="76"/>
</StackPanel>
<StackPanel x:Name="TextConversionOptions" Visibility="Collapsed" Orientation="Horizontal" Margin="10,60,0,0" Height="25" VerticalAlignment="Top" HorizontalAlignment="Left" Width="300">
<StackPanel x:Name="AudioConversionOptions" Visibility="Collapsed" Orientation="Horizontal">
<CheckBox x:Name="AudioConversion" Content="{x:Static s:guiStrings.TextConvertAudio}" ToolTip="{x:Static s:guiStrings.TooltipAudioFormats}" Margin="0,0,7,0" VerticalAlignment="Center" Height="21" HorizontalAlignment="Left"
IsChecked="{Binding Source={x:Static p:Settings.Default}, Path=appConvertAudio, Mode=TwoWay}"/>
</StackPanel>
<StackPanel x:Name="TextConversionOptions" Visibility="Collapsed" Orientation="Horizontal">
<TextBlock Text="{x:Static s:guiStrings.TextEncoding}" Margin="0,0,7,0" TextAlignment="Right" VerticalAlignment="Center" HorizontalAlignment="Right"/>
<ComboBox x:Name="TextEncoding" Margin="0" VerticalAlignment="Center" Height="21" HorizontalAlignment="Right" Width="76"/>
</StackPanel>
</Grid>
<Button Content="{x:Static s:guiStrings.ButtonExtract}" Click="ExtractButton_Click" HorizontalAlignment="Right" Margin="0,0,102.157,10" Width="75" IsDefault="True" Height="25" VerticalAlignment="Bottom" VerticalContentAlignment="Center"/>
<Button Content="{x:Static s:guiStrings.ButtonCancel}" Margin="0,0,10.157,10" IsCancel="True" HorizontalAlignment="Right" Width="75" Height="25" VerticalAlignment="Bottom" VerticalContentAlignment="Center"/>
</Grid>

View File

@ -1,6 +1,6 @@
// Game Resource Browser
//
// Copyright (C) 2014 by morkt
// Copyright (C) 2014-2015 by morkt
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
@ -48,20 +48,40 @@ namespace GARbro.GUI
DestinationDir.EnterKeyDown += acb_OnEnterKeyDown;
if ("image" == entry.Type)
{
ImageConversionOptions.Visibility = Visibility.Visible;
TextConversionOptions.Visibility = Visibility.Collapsed;
ActiveOption = ImageConversionOptions;
InitImageFormats (ImageConversionFormat);
}
else if ("script" == entry.Type)
{
ImageConversionOptions.Visibility = Visibility.Collapsed;
TextConversionOptions.Visibility = Visibility.Visible;
ActiveOption = TextConversionOptions;
TextEncoding.IsEnabled = false;
}
else if ("audio" == entry.Type)
{
ActiveOption = AudioConversionOptions;
}
else
{
ImageConversionOptions.Visibility = Visibility.Collapsed;
TextConversionOptions.Visibility = Visibility.Collapsed;
ActiveOption = null;
}
}
private UIElement m_active_option;
public UIElement ActiveOption
{
get { return m_active_option; }
set
{
if (value == m_active_option)
return;
m_active_option = value;
if (null != m_active_option)
m_active_option.Visibility = Visibility.Visible;
foreach (var c in ConversionTypePanel.Children.Cast<UIElement>())
{
if (c != m_active_option)
c.Visibility = Visibility.Collapsed;
}
}
}
@ -75,7 +95,7 @@ namespace GARbro.GUI
void ExtractButton_Click (object sender, RoutedEventArgs e)
{
this.DialogResult = true;
if (ImageConversionOptions.Visibility == Visibility.Visible)
if (ImageConversionOptions == ActiveOption)
{
ExportImageFormat (ImageConversionFormat);
}

View File

@ -140,6 +140,7 @@
<Compile Include="ExtractFile.xaml.cs">
<DependentUpon>ExtractFile.xaml</DependentUpon>
</Compile>
<Compile Include="GarAudio.cs" />
<Compile Include="GarConvert.cs" />
<Compile Include="GarCreate.cs" />
<Compile Include="GarExtract.cs" />

View File

@ -2,7 +2,7 @@
//! \date Tue Jul 08 12:53:45 2014
//! \brief Game Archive file class.
//
// Copyright (C) 2014 by morkt
// Copyright (C) 2014-2015 by morkt
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
@ -149,7 +149,7 @@ namespace GameRes
/// </summary>
public Stream CreateFile (Entry entry)
{
return m_interface.CreateFile (entry.Name);
return ArchiveFormat.CreateFile (entry.Name);
}
#region IDisposable Members

View File

@ -2,7 +2,7 @@
//! \date Mon Jun 30 20:12:13 2014
//! \brief game resources browser.
//
// Copyright (C) 2014 by morkt
// Copyright (C) 2014-2015 by morkt
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
@ -153,7 +153,7 @@ namespace GameRes
/// Create file corresponding to <paramref name="entry"/> in current directory and open it
/// for writing. Overwrites existing file, if any.
/// </summary>
public Stream CreateFile (string filename)
static public Stream CreateFile (string filename)
{
filename = CreatePath (filename);
if (File.Exists (filename))

71
GarAudio.cs Normal file
View File

@ -0,0 +1,71 @@
//! \file GarAudio.cs
//! \date Thu May 14 13:58:03 2015
//! \brief GARbro audio formats conversions.
//
// Copyright (C) 2015 by morkt
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
// deal in the Software without restriction, including without limitation the
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
// sell copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
// IN THE SOFTWARE.
//
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Windows;
using GameRes;
using GARbro.GUI.Strings;
namespace GARbro.GUI
{
public partial class MainWindow : Window
{
void ExtractAudio (ArcFile arc, Entry entry)
{
using (var file = arc.OpenEntry (entry))
using (var sound = AudioFormat.Read (file))
{
if (null == sound)
throw new InvalidFormatException (string.Format ("{1}: {0}", guiStrings.MsgUnableInterpret, entry.Name));
ConvertAudio (entry.Name, sound);
}
}
public static readonly HashSet<string> CommonAudioFormats = new HashSet<string> { "wav", "mp3", "ogg" };
void ConvertAudio (string entry_name, SoundInput input)
{
string source_format = input.SourceFormat;
if (CommonAudioFormats.Contains (source_format))
{
string output_name = Path.ChangeExtension (entry_name, source_format);
using (var output = ArchiveFormat.CreateFile (output_name))
{
input.Source.Position = 0;
input.Source.CopyTo (output);
}
}
else
{
var wav_format = FormatCatalog.Instance.AudioFormats.Where (f => f.Tag == "WAV").First();
string output_name = Path.ChangeExtension (entry_name, "wav");
using (var output = ArchiveFormat.CreateFile (output_name))
wav_format.Write (input, output);
}
}
}
}

View File

@ -2,7 +2,7 @@
//! \date Fri Jul 25 05:52:27 2014
//! \brief Extract archive frontend.
//
// Copyright (C) 2014 by morkt
// Copyright (C) 2014-2015 by morkt
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
@ -138,8 +138,11 @@ namespace GARbro.GUI
IEnumerable<Entry> file_list = arc.Dir;
bool skip_images = !extractDialog.ExtractImages.IsChecked.Value;
bool skip_script = !extractDialog.ExtractText.IsChecked.Value;
if (skip_images || skip_script)
file_list = file_list.Where (f => !(skip_images && f.Type == "image") && !(skip_script && f.Type == "script"));
bool skip_audio = !extractDialog.ExtractAudio.IsChecked.Value;
if (skip_images || skip_script || skip_audio)
file_list = file_list.Where (f => !(skip_images && f.Type == "image") &&
!(skip_script && f.Type == "script") &&
!(skip_audio && f.Type == "audio"));
if (!file_list.Any())
{
@ -208,7 +211,9 @@ namespace GARbro.GUI
extractProgressDialog.Description = file_list.First().Name;
extractProgressDialog.ProgressBarStyle = ProgressBarStyle.MarqueeProgressBar;
}
bool convert_audio = Settings.Default.appConvertAudio;
int extract_count = 0;
Exception pending_error = null;
extractProgressDialog.DoWork += (s, e) =>
{
try
@ -222,6 +227,8 @@ namespace GARbro.GUI
extractProgressDialog.ReportProgress (extract_count*100/total, null, entry.Name);
if (null != image_format && entry.Type == "image")
ExtractImage (arc, entry, image_format);
else if (convert_audio && entry.Type == "audio")
ExtractAudio (arc, entry);
else
arc.Extract (entry);
++extract_count;
@ -229,7 +236,7 @@ namespace GARbro.GUI
}
catch (Exception X)
{
SetStatusText (X.Message);
pending_error = X;
}
};
extractProgressDialog.RunWorkerCompleted += (s, e) => {
@ -241,6 +248,8 @@ namespace GARbro.GUI
Dispatcher.Invoke (RefreshView);
}
SetStatusText (Localization.Format ("MsgExtractedFiles", extract_count));
if (null != pending_error)
PopupError (pending_error.Message, guiStrings.MsgErrorExtracting);
};
extractProgressDialog.ShowDialog (this);
}

View File

@ -309,5 +309,29 @@ namespace GARbro.GUI.Properties {
this["appLastImageFormat"] = value;
}
}
[global::System.Configuration.UserScopedSettingAttribute()]
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
[global::System.Configuration.DefaultSettingValueAttribute("False")]
public bool appConvertAudio {
get {
return ((bool)(this["appConvertAudio"]));
}
set {
this["appConvertAudio"] = value;
}
}
[global::System.Configuration.UserScopedSettingAttribute()]
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
[global::System.Configuration.DefaultSettingValueAttribute("True")]
public bool appExtractAudio {
get {
return ((bool)(this["appExtractAudio"]));
}
set {
this["appExtractAudio"] = value;
}
}
}
}

View File

@ -74,5 +74,11 @@
<Setting Name="appLastImageFormat" Type="System.String" Scope="User">
<Value Profile="(Default)">PNG</Value>
</Setting>
<Setting Name="appConvertAudio" Type="System.Boolean" Scope="User">
<Value Profile="(Default)">False</Value>
</Setting>
<Setting Name="appExtractAudio" Type="System.Boolean" Scope="User">
<Value Profile="(Default)">True</Value>
</Setting>
</Settings>
</SettingsFile>

View File

@ -756,6 +756,15 @@ namespace GARbro.GUI.Strings {
}
}
/// <summary>
/// Looks up a localized string similar to Convert audio to common format.
/// </summary>
public static string TextConvertAudio {
get {
return ResourceManager.GetString("TextConvertAudio", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Convert images.
/// </summary>
@ -801,6 +810,15 @@ namespace GARbro.GUI.Strings {
}
}
/// <summary>
/// Looks up a localized string similar to Extract audio.
/// </summary>
public static string TextExtractAudio {
get {
return ResourceManager.GetString("TextExtractAudio", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Extract images.
/// </summary>
@ -873,6 +891,15 @@ namespace GARbro.GUI.Strings {
}
}
/// <summary>
/// Looks up a localized string similar to Either WAV, MP3 or OGG.
/// </summary>
public static string TooltipAudioFormats {
get {
return ResourceManager.GetString("TooltipAudioFormats", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Back.
/// </summary>

View File

@ -399,4 +399,13 @@ Overwrite?</value>
<data name="LabelEncoding" xml:space="preserve">
<value>Encoding</value>
</data>
<data name="TextConvertAudio" xml:space="preserve">
<value>Convert audio to common format</value>
</data>
<data name="TextExtractAudio" xml:space="preserve">
<value>Extract audio</value>
</data>
<data name="TooltipAudioFormats" xml:space="preserve">
<value>Either WAV, MP3 or OGG</value>
</data>
</root>

View File

@ -414,4 +414,13 @@
<data name="LabelEncoding" xml:space="preserve">
<value>Кодировка</value>
</data>
<data name="TextConvertAudio" xml:space="preserve">
<value>Преобразовывать аудио в стандартный формат</value>
</data>
<data name="TextExtractAudio" xml:space="preserve">
<value>Извлекать аудио</value>
</data>
<data name="TooltipAudioFormats" xml:space="preserve">
<value>WAV, MP3, либо OGG</value>
</data>
</root>