public unsafe bool Transcode(uint imageIndex, uint levelIndex, TranscodeFormat format, out byte[] transcodedData)
        {
            Profiler.BeginSample("BasisU.Transcode");
            transcodedData = null;

            if (!ktx_basisu_startTranscoding(nativeReference))
            {
                Profiler.EndSample();
                return(false);
            }

            var size = GetImageTranscodedSize(imageIndex, levelIndex, format);

            byte[] data = new byte[size];

            bool result = false;

            fixed(void *dst = &(data[0]))
            {
                result = ktx_basisu_transcodeImage(nativeReference, dst, size, imageIndex, levelIndex, (uint)format, 0, 0);
            }

            transcodedData = data;
            Profiler.EndSample();
            return(result);
        }
Пример #2
0
    public static bool GetPreferredFormat(out TextureFormat unityFormat, out TranscodeFormat transcodeFormat, bool hasAlpha = false)
    {
        unityFormat     = TextureFormat.DXT1;
        transcodeFormat = TranscodeFormat.BC1;

        var formats = hasAlpha
            ? alphaFormatDict
            : opaqueFormatDict;

        foreach (var format in formats)
        {
            var supported = SystemInfo.SupportsTextureFormat(format.Key);
            if (supported)
            {
                unityFormat     = format.Key;
                transcodeFormat = format.Value;
                return(true);
            }
        }
        if (hasAlpha)
        {
            // Fallback to opaque texture format
            var opaqueFound = GetPreferredFormat(out unityFormat, out transcodeFormat, false);
            if (opaqueFound)
            {
                Debug.LogWarningFormat("No supported alpha format found. Fallback to opaque format {0} ({1})", transcodeFormat, unityFormat);
            }
            return(opaqueFound);
        }
        return(false);
    }
Пример #3
0
        public unsafe static JobHandle LoadBytesJob(
            ref BasisUniversalJob job,
            BasisUniversalTranscoderInstance basis,
            NativeSlice <byte> basisuData,
            TranscodeFormat transF
            )
        {
            Profiler.BeginSample("BasisU.LoadBytesJob");

            var  numLevels = basis.GetLevelCount(job.imageIndex);
            var  sizes     = new NativeArray <uint>((int)numLevels, KtxNativeInstance.defaultAllocator);
            var  offsets   = new NativeArray <uint>((int)numLevels, KtxNativeInstance.defaultAllocator);
            uint totalSize = 0;

            for (uint i = 0; i < numLevels; i++)
            {
                offsets[(int)i] = totalSize;
                var size = basis.GetImageTranscodedSize(job.imageIndex, i, transF);
                sizes[(int)i] = size;
                totalSize    += size;
            }

            job.format          = transF;
            job.sizes           = sizes;
            job.offsets         = offsets;
            job.nativeReference = basis.nativeReference;

            job.textureData = new NativeArray <byte>((int)totalSize, KtxNativeInstance.defaultAllocator);

            var jobHandle = job.Schedule();

            Profiler.EndSample();
            return(jobHandle);
        }
Пример #4
0
        private async Task <APIResponse> GetSong(APIRequest request)
        {
            var song         = MediaDatabase.GetSong(request.Segment);
            var responseData = song.HasValue ? new Dictionary <string, object>()
            {
                { "song", song }
            } : null;

            //handle transcode request
            if (song != null && request.Params != null && request.Params.ContainsKey("transcode"))
            {
                string          sourceFilePath     = MediaDatabase.GetSongPath(request.Segment);
                string          transcodedFilePath = null;
                TranscodeFormat format             = TranscodeFormat.Undefined;;

                if (request.Params.ContainsKey("transcode"))
                {
                    if (Enum.TryParse <TranscodeFormat>(request.Params["transcode"], true, out format))
                    {
                        transcodedFilePath = await MediaTranscoder.GetFromCacheOrTranscodeAsync(request.Segment, sourceFilePath, format);
                    }
                    else
                    {
                        throw new NotSupportedException($"Transcode format \"{request.Params["transcode"]}\" is not recognized!");
                    }
                }

                if (!request.Params.ContainsKey("return") || request.Params["return"] == "path")
                {
                    responseData.Add("transcodedPath", transcodedFilePath);
                }
                else
                {
                    if (request.Params["return"] == "field")
                    {
                        byte[] data = File.ReadAllBytes(transcodedFilePath);
                        responseData.Add("transcodedData", data);
                    }
                    else if (request.Params["return"] == "body")
                    {
                        byte[] data = File.ReadAllBytes(transcodedFilePath);
                        return(new APIResponse(null, (int)HttpStatusCode.OK, format.GetContentType(), data));
                    }
                    else
                    {
                        throw new NotImplementedException();
                    }
                }
            }

            return(new APIResponse(JsonConvert.SerializeObject(new { data = responseData })));
        }
        public unsafe JobHandle LoadBytesJob(
            ref KtxTranscodeJob job,
            TranscodeFormat transF
            )
        {
            UnityEngine.Profiling.Profiler.BeginSample("Ktx.LoadBytesJob");

            job.result          = new NativeArray <KtxErrorCode>(1, defaultAllocator);
            job.nativeReference = nativeReference;
            job.outputFormat    = transF;

            var jobHandle = job.Schedule();

            UnityEngine.Profiling.Profiler.EndSample();
            return(jobHandle);
        }
Пример #6
0
    void LoadTextureKtx(string file, TranscodeFormat transF, GraphicsFormat gf)
    {
        if (currentGo != null)
        {
            Destroy(currentGo);
        }
        var txt = new KtxTestTexture();

        txt.graphicsFormat = gf;
        txt.transF         = transF;

        var testLoader = Object.Instantiate <TestKtxFileLoader>(prefab);

        testLoader.overrideTexture = txt;
        testLoader.filePath        = file;
        currentGo = testLoader.gameObject;
    }
Пример #7
0
        public static string GetContentType(this TranscodeFormat format)
        {
            switch (format)
            {
            case TranscodeFormat.Wave:
                return("audio/wav");

            case TranscodeFormat.Vorbis:
                return("audio/ogg");

            case TranscodeFormat.MP3:
                return("audio/mpeg");

            case TranscodeFormat.Flac:
                return("audio/flac");

            default:
                return("application/octet-stream");
            }
        }
Пример #8
0
        public unsafe static JobHandle LoadBytesJob(
            ref BasisUniversalJob job,
            BasisUniversalTranscoderInstance basis,
            NativeArray <byte> basisuData,
            TranscodeFormat transF
            )
        {
            Profiler.BeginSample("BasisU.LoadBytesJob");

            var size = basis.GetImageTranscodedSize(0, 0, transF);

            job.format          = transF;
            job.size            = size;
            job.nativeReference = basis.nativeReference;

            job.textureData = new NativeArray <byte>((int)size, KtxNativeInstance.defaultAllocator);

            var jobHandle = job.Schedule();

            Profiler.EndSample();
            return(jobHandle);
        }
Пример #9
0
        public unsafe bool Transcode(uint imageIndex, uint levelIndex, TranscodeFormat format, out byte[] transcodedData)
        {
            transcodedData = null;

            if (!aa_startTranscoding(nativeReference))
            {
                return(false);
            }

            var size = GetImageTranscodedSize(imageIndex, levelIndex, format);

            byte[] data = new byte[size];

            bool result = false;

            fixed(void *dst = &(data[0]))
            {
                result = aa_transcodeImage(nativeReference, dst, size, imageIndex, levelIndex, (uint)format, 0, 0);
            }

            transcodedData = data;
            return(result);
        }
 public uint GetImageTranscodedSize(uint imageIndex, uint levelIndex, TranscodeFormat format)
 {
     return(ktx_basisu_getImageTranscodedSizeInBytes(nativeReference, imageIndex, levelIndex, (uint)format));
 }
 public FormatInfo(TextureFeatures features, GraphicsFormat format, TranscodeFormat transcodeFormat)
 {
     this.features = features;
     this.formats  = new TranscodeFormatTuple(format, transcodeFormat);
 }
 public TranscodeFormatTuple(GraphicsFormat format, TranscodeFormat transcodeFormat)
 {
     this.format          = format;
     this.transcodeFormat = transcodeFormat;
 }
 public static extern KtxErrorCode ktxTexture2_TranscodeBasis(System.IntPtr ktxTexture, TranscodeFormat outputFormat, uint transcodeFlags);
Пример #14
0
        /// <summary>
        /// Transcodes a music file
        /// </summary>
        /// <returns>The path of the transcoded file</returns>
        public static async Task <string> GetFromCacheOrTranscodeAsync(string hash, string path, TranscodeFormat format)
        {
            string commandLine;
            string extension;

            switch (format)
            {
            case TranscodeFormat.Wave:
                commandLine = waveCommandLine;
                extension   = "wav";
                break;

            case TranscodeFormat.Vorbis:
                commandLine = vorbisCommandLine;
                extension   = "ogg";
                break;

            //case TranscodeFormat.MP3:
            //    break;
            default:
                throw new NotSupportedException($"Specified format \"{format}\" is not supported for transcoding");
            }

            string encodedHash = HashUtils.HexStringToBase64String(hash);
            string targetPath  = Path.GetFullPath(Path.Combine(Config.CacheFolderPath, $"{encodedHash}.{extension}"));

            if (File.Exists(targetPath))
            {
                Console.WriteLine($"[MediaTranscoder] Retrieving {hash} from cache ({targetPath})");

                //I guess this is a nop
            }
            else
            {
                Console.WriteLine($"[MediaTranscoder] Transcoding {hash} to cache ({targetPath})");

                string sourcePath = Path.GetFullPath(path);
                //invoke ffmpeg and wait for exit
                await Task.Run(() =>
                {
                    Process p                          = new Process();
                    p.StartInfo.Arguments              = string.Format(commandLine, sourcePath, targetPath);
                    p.StartInfo.WorkingDirectory       = Config.ProgramFolderPath;
                    p.StartInfo.FileName               = "ffmpeg.exe";
                    p.StartInfo.CreateNoWindow         = true;
                    p.StartInfo.RedirectStandardError  = true;
                    p.StartInfo.RedirectStandardOutput = true;

                    p.Start();
                    p.WaitForExit();

                    string output = p.StandardOutput.ReadToEnd();
                    string error  = p.StandardError.ReadToEnd(); //ffmpeg seems to toss everything into stderr for some reason

                    //Console.WriteLine(output);
                    //Console.WriteLine(error);
                    //Console.WriteLine();

                    if (!File.Exists(targetPath))
                    {
                        throw new TranscodingFailedException(error);
                    }
                });
            }

            return(targetPath);
        }