mtasa-blue icon indicating copy to clipboard operation
mtasa-blue copied to clipboard

Gif player

Open MobinYengejehi opened this issue 3 years ago • 49 comments

hi i made a gif player which load and play gifs as fast as possible you can create a gif like:

local gif = gifCreate(file_path or gif_buffer) -- "logo.gif" for example

local size = Vector2(dxGetMaterialSize(gif))

addEventHandler("onClientRender",getRootElement(),function()
    if isElement(gif) then
        dxDrawImage(0,0,size,gif)
    end
end)

cuz it is a texture element you can use it, inside shaders or inside all dx related functions

MobinYengejehi avatar Dec 16 '22 09:12 MobinYengejehi

Thanks for the pull request! Cool idea!

I'm wondering if there is an open source Gif loader library out there that we could use instead of implementing the intricacies ourselves, thinking from a future maintainability and security perspective.

patrikjuvonen avatar Dec 16 '22 10:12 patrikjuvonen

Great. But I think you should use the new Lua parser.

tederis avatar Dec 16 '22 10:12 tederis

Thanks for the pull request! Cool idea!

I'm wondering if there is an open source Gif loader library out there that we could use instead of implementing the intricacies ourselves, thinking from a future maintainability and security perspective.

yeah we can i just used https://github.com/hidefromkgb/gif_load and made it a little better because it needed some changes. you can go and see the real code. it is from @hidefromkgb i thought that we must write code like this this is my first time trying to contribute mta-blue

MobinYengejehi avatar Dec 16 '22 10:12 MobinYengejehi

is there any other problems that i should solve?

MobinYengejehi avatar Dec 16 '22 19:12 MobinYengejehi

In my opinion your solution is over engineered, instead i propose to make "createGif" returns a regular texture ( texture atlas ) + number of frames.

CrosRoad95 avatar Dec 17 '22 13:12 CrosRoad95

it does. it will return a texture element that is gif and if you want to get frames you can use gifGetFrameCount(element gif) and also it has a player that you can play or stop or you can set its speed too for example:

local gif = gifCreate("img.gif")
local width,height = dxGetMaterialSize(gif)

-- you can adjust the delay of each frame
local newDelay = 5 -- ms : 5*(10^-3) s
-- 5 ms can make gif really fast!

local frameCount = gifGetFrameCount(gif)
for frame = 1,frameCount do -- for all frames
    gifSetFrameDelay(gif,frame,newDelay)
end

--

gifPlay(gif) -- play the gif

addEventHandler("onClientRender",root,function()
    if isElement(gif) then
        dxDrwaImage(0,0,width,height,gif)
    end
end)

it s really not that hard!

MobinYengejehi avatar Dec 17 '22 16:12 MobinYengejehi

in my opinion these all functions are useless, it is trivial to calculate what frame should be displayed and calculating uv coors is not a rocket science

CrosRoad95 avatar Dec 17 '22 16:12 CrosRoad95

but i think they can be useful ! for example imagine you are writing a phone script and you have an application like *whatsapp for making that you have 2 ways: 1- using browser -- which is hard to load on weak computers (that in some countries most of the people who are playing MTA have) 2- using dx functions if you choose the dx interface you need some functions that will allow you to control your gifs and many other ideas that scripters can have when they want to use dx functions instead of browser

MobinYengejehi avatar Dec 17 '22 17:12 MobinYengejehi

but your opinion is respected and if you want we can remove them

MobinYengejehi avatar Dec 17 '22 17:12 MobinYengejehi

IMHO, half useless function. There aren't any questions about implementation for this. But, sorry, all world is trying to move out from GIF to APNG, WEBP, and Lottie of course, modern things for today. Even huge GIF hostings are storing GIFs in MP4 format.

Disinterpreter avatar Dec 24 '22 13:12 Disinterpreter

Ok

MobinYengejehi avatar Dec 31 '22 18:12 MobinYengejehi

well i removed useless functions. the functions that have been removed are:

gifGetTick(element [gif (dx material)]); -> int, boolean
gifGetFormat(element [gif (dx material)]); -> string, boolean
gifGetFrameDelay(element [gif (dx material)], int [frame index]); -> int, boolean
gifSetFrameDelay(element [gif (dx material)], int [frame index], int [delay]); -> boolean
gifGetShowingFrame(element [gif (dx material)]); -> int
gifGetFrameDefaultDelay(element [gif (dx material)], int [frame index]); -> int
gifGetFrameCount(element [gif (dx material)]); -> int

and the remaining functions are:

gifCreate(string [path or rawdata]); -> gif element (dx material) -- this function creates a gif element
gifPlay(element [gif (dx material)]); -> boolean -- this function plays the gif if it is stopped
gifStop(element [gif (dx material)]); -> boolean -- this function stops the gif if it is playing
gifNavigateToThumbnail(element [gif (dx material)]); -> boolean -- this function shows the first frame
isGifPlaying(element [gif (dx material)]); -> boolean -- this function checks if gif is playing or not

MobinYengejehi avatar Jan 13 '23 17:01 MobinYengejehi

i hope it will be ok this time!

MobinYengejehi avatar Jan 13 '23 17:01 MobinYengejehi

Maybe implementing gifSetShowingFrame instead of gifNavigateToThumbnail will be better. And isGifPlaying should be gifIsPlaying

thisdp avatar Jan 14 '23 03:01 thisdp

for gifSetShowingFrame i think gif player needs some functions like gifGetShowingFrame & gifGetFrameCount but i removed them cuz your friends said it should be simple i can return them if you want

and isGifPlaying changed to gifIsPlaying!

MobinYengejehi avatar Jan 14 '23 05:01 MobinYengejehi

gifPlay

then, maybe we can specify the first frame in gifPlay or gifStop, in this way gifNavigateToThumbnail can be removed.

thisdp avatar Jan 14 '23 05:01 thisdp

then can i return gifGetFrameCount and gifGetShowingFrame?

MobinYengejehi avatar Jan 14 '23 05:01 MobinYengejehi

then can i return gifGetFrameCount and gifGetShowingFrame?

maybe gifGetDetails, or gifGetProperty/gifSetProperty

thisdp avatar Jan 14 '23 05:01 thisdp

ah yeah your right this one is better i will do it now

MobinYengejehi avatar Jan 14 '23 05:01 MobinYengejehi

ah yeah your right this one is better i will do it now

gifGetProperty(gif,"delay") gifSetProperty(gif,"delay",100)

thisdp avatar Jan 14 '23 05:01 thisdp

delay works per frame i mean each frame has a different delay like gifSetFrameDelay(gif, frame, delay)

MobinYengejehi avatar Jan 14 '23 06:01 MobinYengejehi

what should we do for it?

MobinYengejehi avatar Jan 14 '23 06:01 MobinYengejehi

delay works per frame i mean each frame has a different delay like gifSetFrameDelay(gif, frame, delay)

then, maybe gifSetProperty(gif,frame,"delay",100) for frame property. If frame is not specified, the property will be global

thisdp avatar Jan 14 '23 06:01 thisdp

aha ok after 30 minutes i finish them

MobinYengejehi avatar Jan 14 '23 06:01 MobinYengejehi

and i think it is better we set showing frame with gifSetProperty(gif,"showing_frame",frameindex) too whats your opinion? isn't it better?

MobinYengejehi avatar Jan 14 '23 06:01 MobinYengejehi

and i think it is better we set showing frame with gifSetProperty(gif,"showing_frame",frameindex) too whats your opinion?

Good idea

thisdp avatar Jan 14 '23 06:01 thisdp

In this way, gifCreate, gifPlay, gifStop and gifIsPlaying will be mainly used functions. For rarely used functions, we can just use gifSetProperty/gifGetProperty.

thisdp avatar Jan 14 '23 06:01 thisdp

Better to use new lua parser. Refer to #2535

thisdp avatar Jan 14 '23 08:01 thisdp

gifGetProperty return types are string or number how should i return something like that when im using new lua parser?

MobinYengejehi avatar Jan 14 '23 08:01 MobinYengejehi

gifGetProperty return types are string or number how should i return something like that when im using new lua parser?

for example: std::variant<bool, CLuaMultiReturn<char, char>>

and you can even use this for passing arguments: std::variant<bool, float> argumentN

thisdp avatar Jan 14 '23 08:01 thisdp