Roblox Video Player

Hey, i wonder if you can make the output of the display using NPC, lol

idk just for fun? like in this video

5 Likes

then why roblox moderate my anime girl instead the anime boy isn’t moderated :123:

3 Likes

I’m slowly getting there :eyes: Screen capture - 37fb4f7f3fdd50fb49688eac25726332 - Gyazo

This uses a web server tho so it might be a little more difficult to setup.

1 Like

ayyyy niceeee

I don’t mind how hard is it to set up as long I learn new thing with this, then it going to be good

2 Likes

Update! I’ve managed to encode an entire video without uploading each frame/image into roblox itself.

Here’s an example:

It isn’t exactly synced, but there is an option to do so.

Keep in mind that this only works locally. This means that this project can only run in roblox studio, not the roblox player. Roblox has a HTTP get request limitation that I’ve not found a way around. Please inform me of any other way I can get past this. (Other than sending requests in chunks and enforcing a cooldown).

Anyways, onto the setup.

Things you need:

  1. Get the code and roblox place file from this GitHub repository. In it, you should find a folder named “Resources”.

  2. Any Integrated Development Environment (IDE). I use Visual Studio.

  3. Install the Flask python library

Setup:

  1. Open up the “Resources” folder with your IDE
    image

  2. Place the video (.mp4) you want to encode into the “Videos” folder
    image

  3. Create an empty text (.txt) file in the “PixelData” folder and name it whatever you want. I’d suggest naming it somthing similar or the same as the video title for convenience.
    image

  4. In the “PixelDataEncoder” python file (.py), you should find this line of code near the bottom.


    There are 3 commas separating the 4 information/arguments that you need to input into here.
    Arguments:
    i) Video file location, just change “BadApple” to whatever you named your video.

    ii) Resolution multiplier. Values less than 1 will decrease the resolution while values more than 1 will cause unnecessary lag. Stick to values 1 and below which is a positive number.

    iii) Frames Per Second. Pretty self explanatory. You can check your video’s frame per second by right clicking the .mp4 file in your file explorer, selecting “Properties” and going to the “Details” tab.


    iv) Colour. Put “True” if you’d like your video in colour and “False” if you’d like it to be a grey scale. File sizes with grey scale will be smaller (Remember this option).

  5. Find this line of code and change it to the location of the empty text file you’ve created.
    image

  6. If all inputs are properly inserted, run the code and this should pop up.
    image

    Ensure that “Encryption Completed” pops up before closing the console. Otherwise, the encoded data will not save.

    IMPORTANT NOTE: DO NOT OPEN THE TEXT FILE, YOU WILL FREEZE OR MAYBE EVEN CRASH YOUR IDE. You can try to, but that’s your call.

You have now encoded your video into pixels. We’ll work on the web server next.

  1. Open up the python file named “WebServer”.
    image

Find this line and change the file path to your encoded text file’s path. After changing, run the code and leave it running whenever you need to play a video. (Remember, this version only runs locally. This means that it’ll only work if the web server and roblox is using the same IP address)(I might be wrong)

The web server should be done. Finally, let’s set everything up in roblox studio.

  1. In the roblox place file (.rbxl), open up the data module script which is at “ServerScriptService” > “FilmHandlerPixels” > “PixelFilmData”.
    image

Find this section of code, change the configurations accordingly.


Things to note:
i) Remember what you put for “Title” as the code will use this to find the correct set of data.

ii) If you have disabled colour during the encoding process in python, you should disable it here too.

iii) If you have a sound id, “FPS” is not required and vice versa. Put SoundId as nil if you do not have a sound id. The FPS option didn’t work properly the last time I tested it, but who knows what will happen. Using a sound id is the preferred method.

iv) PlaybackSpeed will affect the playback speed of the entire video (audio and display).

v) A positive sound offset will drag the audio (play it later), while a negative sound offset will play the audio ahead (play it earlier). This is in seconds.

  1. Open up the “FilmHandlerPixels” script, scroll all the way down and find this line
    image
    image
    There are 2 arguments for you to configure here.
    Arguments:
    i) Film title. This is the same “Title” you’ve inserted into the module script.

    ii) Monitor name. This can be found in a folder named “Monitors” under workspace. Change the name if you wish.
    image

  2. Run roblox studio. Give it some time to get and decode the data. The output should look like this.

External Credits
Web Server Code by @WhosThatGuy_Guys

After all that, everything should be good to go! Feel free to let me know if anything is missing or if you have any questions.

I’ve tried using replit to host the code online and UptimeRobot to ping replit every few minutes to keep it running. But roblox’s request limit is still an issue sooooo

I’ve decided to move on from Roblox and Roblox development. It has been a fun few years and this platform has really shaped me into who I am today. I’ll definitely come back someday, just not anytime soon. I’ll still be active on the dev forums tho. Really, thank you all for being so supportive!

16 Likes

This is not going to be performant at all (trust me, I’ve made a roblox screenshare which runs at a whopping 128x72 2fps. Any higher resolution and your ping skyrockets to 200k)

Still cool though!

Though if it only works locally anyway you should probably use Pillow and pythoncv and import rbxtemp images, that would make this more performant and give it a higher resolution.

5 Likes

it CAN be performant if you make it binary, which is what i did and it can run fast enough
the biggest problem right now is updating pixels without lag
ping is also very stable
i also capped fps to 8 because of the request limit, but i thought of a solution (will add soon)

6 Likes

Updating pixels without lag was my problem too.
Though I do wonder - how’d you make it pure binary? From what I know Roblox requests only parse text

2 Likes

no thats a lie, it can return bytes too (they are all on a string)
get them with string.byte

2 Likes

it’s possible to run on client (gui) ? (using image methode)

3 Likes

and for convert video to png simply use shotcut

3 Likes

It should be possible, you just have to change the surface gui to a screen gui, and you’ll have to make some (or all) aspects local.

1 Like

Can you please teach me how using binary can be done? I’ve done a lot of research and tried to implement it in a lot of ways but I’m not sure how.

to be honest that deserves a tutorial on its own but here are the basics

so you probably know that a bit is either 0 or 1
now imagine you got 8 bits which are 256 possible combinations (2^8 = 256)
you can convert these 8 bits into an integer depending on which combination it’s on
an integer is a number that cannot have decimals (for example 0.5 are impossible for integers)

there are unsigned and signed integers:

  • signed integers are able to become negative
  • unsigned integers cannot become negative but has around 2 times more positive numbers than a signed integer has

so an unsigned 8-bit integer will range from 0 to 255 (notice how there are 256 combinations and they are used to make numbers)
and a signed 8-bit integer will range from -128 to 127

now that you know all of that lets make a script

bytes in lua are stored in strings
there are 2 functions in lua that are very useful for these things
string.byte and string.char
basically string.char will convert any number ranging from 0 to 255 into an unsigned 8-bit integer
and string.byte will retrieve unsigned 8-bit integer(s) from a string

EXAMPLE
in this script i will convert a number (which will be 214) into an unsigned 8-bit integer
and then i will retrieve the number from the integer

local uint8=string.char(214); -- uint8 is short for unsigned 8-bit integer
print(type(uint8)) -- it is indeed a string and 214 is stored in there as an unsigned 8-bit integer
local fromUInt8=string.byte(uint8); -- retrieving the number from the string (which contains an uint8)
print(fromUInt8); -- 214

for now im too lazy to continue typing this but i might do it soon (or never)

3 Likes

are the pixels pre-set or do they get set every frame?

1 Like

They get set every frame. I was thought that I’d be too laggy to have more than one set of pixels.

1 Like

i was able to get 60fps on my 200x200 rasterizer by when creating the frames saving their instance in a table and updating it from there. it’s important not to do some string search up as it would make it drastically slower.

1 Like

how?
ive done everything i could to optimize my code yet the game still runs low on fps for resolutions higher than 240x135

just by removing this line the game runs at 60 fps (even on high resolutions)
pixel.Color=rgb(R,G,B)

1 Like

i told him how in my reply, you reference it in a table on start up. how do you reference pixel

2 Likes

i have already done that
all the pixels are in an array

this is how it loops
for i,pixel in ipairs(pixels) do

1 Like