|
| 1 | +# iw3-player |
| 2 | + |
| 3 | +[日本語](README_ja.md) |
| 4 | + |
| 5 | +iw3-player is a self-hosted, specialized viewing environment for stereoscopic media. |
| 6 | +It allows you to stream media converted to 3D via **iw3** from your PC and enjoy it on VR devices through a WebXR application. |
| 7 | + |
| 8 | +The player supports a wide range of operations for stereo media. |
| 9 | +One of its features is to instantly adjust people in photos to life-size. |
| 10 | +Viewing photos at a realistic scale significantly enhances immersion and brings your memories to life in VR. |
| 11 | + |
| 12 | +[Screenshots]() |
| 13 | + |
| 14 | +## Operating Environment |
| 15 | + |
| 16 | +- **Backend (Python)**: Confirmed to work on Linux and Windows. |
| 17 | +- **Frontend (JavaScript)**: Confirmed to work on Meta Quest 2 browser, PC Google Chrome, and Android smartphones. |
| 18 | + |
| 19 | +## Supported Formats |
| 20 | + |
| 21 | +- **Images**: `.png`, `.jpg`, `.jpeg`, `.webp` |
| 22 | +- **Videos**: `.mp4`, `.mkv`, `.webm`. |
| 23 | +- **Archives**: `.zip` |
| 24 | + |
| 25 | +Supported video formats depend on the browser. The Meta Quest 2 browser supports all combinations of mp4, mkv, h264, and h265 commonly used in iw3. The PC version of Google Chrome does not support h265. |
| 26 | +On Meta Quest 2, 4K videos played smoothly. |
| 27 | + |
| 28 | +The player supports both embedded subtitle streams and external files (`.srt` / `.vtt`). External files named identically to the video will be prioritized. Embedded subtitles are automatically converted to `.vtt` by the backend for seamless streaming. |
| 29 | + |
| 30 | +The stereo format is estimated according to the tags in the filename output by iw3. Even if there is no stereo format tag in the filename, if it exists in the parent folder, it will be used. In the case of an archive, the filename of the archive is also used. |
| 31 | + |
| 32 | +## How to Start |
| 33 | + |
| 34 | +### Windows |
| 35 | + |
| 36 | +Execute `iw3-player-gui.bat` to launch the graphical user interface (GUI). |
| 37 | +If `iw3-player-gui.bat` is missing, run `update.bat` followed by `update-installer.bat` to generate it. |
| 38 | + |
| 39 | +[Image]() |
| 40 | + |
| 41 | +### Command Line (CLI) |
| 42 | + |
| 43 | +You can also start the server using the following commands: |
| 44 | + |
| 45 | +**GUI Mode** |
| 46 | +```bash |
| 47 | +python -m iw3.player.gui |
| 48 | +``` |
| 49 | + |
| 50 | +**CLI Mode** |
| 51 | +```bash |
| 52 | +python -m iw3.player --root /path/to/your/media |
| 53 | +``` |
| 54 | + |
| 55 | +Once the server is running, access the URL displayed in the terminal or GUI (e.g., `https://[IP address]:1304`) using the browser on your VR device. |
| 56 | + |
| 57 | +#### About SSL Warnings |
| 58 | + |
| 59 | +To meet WebXR's mandatory HTTPS requirement for local streaming, the iw3-player backend generates a self-signed certificate on startup. |
| 60 | + |
| 61 | +During your first visit, your browser will display a security warning (e.g., "Your connection is not private"). This is expected. To proceed: |
| 62 | + |
| 63 | +1. Click **"Advanced"**. |
| 64 | +2. Select **"Proceed to [IP address]"**. |
| 65 | + |
| 66 | +**Tip:** Bookmarking this page will allow you to skip this warning in the future. |
| 67 | + |
| 68 | +While browsers typically discourage trusting local servers in this manner, it is a necessary workaround for local WebXR development. |
| 69 | + |
| 70 | +## Each Operation and Setting Screens |
| 71 | + |
| 72 | +## UI and Controls |
| 73 | + |
| 74 | +### Basic VR Controller Operations |
| 75 | + |
| 76 | +- **Menu Toggle**: Trigger, B, or Y buttons. |
| 77 | +- **Select/Confirm**: Trigger (Index finger). |
| 78 | +- **Navigate Images**: Tilt thumbstick Left/Right (during image playback). |
| 79 | +- **Seek**: Tilt thumbstick Left/Right (during video playback). |
| 80 | +- **Page Navigation**: Tilt thumbstick Up/Down (in File Explorer). |
| 81 | + |
| 82 | +Additional screen-specific shortcuts are detailed in the **Screen Settings** section below. |
| 83 | + |
| 84 | +#### Screen Settings |
| 85 | + |
| 86 | +This is the most frequently used menu, allowing you to fine-tune the screen's shape and its position in 3D space. |
| 87 | + |
| 88 | +| Item | Shortcut | Description | |
| 89 | +| :--- | :--- | :--- | |
| 90 | +| `Screen Size` | `[Grip + Stick X]` | Physical size of the virtual screen | |
| 91 | +| `Tilt` | `[Trigger + Tilt]` | Vertical tilt of the screen | |
| 92 | +| `Distance` | `[Stick Y]` | Distance from the viewer (Zoom) | |
| 93 | +| `Scale` | `[Grip + Stick Y]` | Adjusts stereoscopic disparity (Apparent object size) | |
| 94 | +| `Pos X` / `Pos Y` | `[Grip + Move]` | Move screen horizontally or vertically | |
| 95 | +| `Curvature` | - | Adjusts the horizontal curve of the screen | |
| 96 | +| `Edge Fade` | - | Smoothly fades out the edges of the screen | |
| 97 | +| `Background` | - | Adjusts background brightness (Ignored if a skybox is active) | |
| 98 | + |
| 99 | +*Note: These operations can sometimes result in perceptual effects that differ from the literal mechanical change. We highly recommend reading the [Screen Operation and Perception](#screen-operation-and-perception) section for the best experience.* |
| 100 | + |
| 101 | +#### Color Settings |
| 102 | + |
| 103 | +Apply real-time color correction and image enhancements. While most media looks best with default settings, these tools are invaluable for specific sources. |
| 104 | + |
| 105 | +- **LUT (Color Profile)**: Select from various cinematic or technical color profiles. |
| 106 | +- **Adjustments**: Fine-tune `Contrast`, `Brightness`, `Hue`, `Saturation`, and `Gamma`. |
| 107 | + |
| 108 | +You can add custom LUTs by placing `.cube` files in the `public/lut/` directory. |
| 109 | +Using `haldclut2cube.py`, you can convert the effect applied to [Identity HaldCLUT image](https://rawpedia.rawtherapee.com/File:Hald_CLUT_Identity.tif) into a `.cube` file. |
| 110 | + |
| 111 | +#### Env Settings (Environment) |
| 112 | + |
| 113 | +Customize your virtual theater. While not strictly necessary for viewing, watching media under a high-fidelity sky can greatly improve the experience. |
| 114 | + |
| 115 | +- **Skybox**: Set a 360-degree background image and adjust its orientation and brightness. |
| 116 | +- **3D Model**: Load a scene model (e.g., a floor or environment) to ground your experience. |
| 117 | + |
| 118 | +Custom backgrounds (`.hdr` or `.exr`) and models (`.glb`) can be added to the `public/environments/` directory. High-quality HDRI and IBL assets are available at [Poly Haven](https://polyhaven.com/) and [ambientCG](https://ambientcg.com/). Scenes created in Blender can be exported as `.glb` (supporting Draco compression and animations) for use here. |
| 119 | + |
| 120 | +#### Subtitle Settings |
| 121 | + |
| 122 | +Configuration for video subtitles. |
| 123 | + |
| 124 | +- Toggle subtitles ON/OFF. |
| 125 | +- Switch between multiple subtitle tracks. |
| 126 | +- Adjust **Vertical Position**, **Depth**, **Font Size**, and **Eye Separation** (disparity). |
| 127 | + |
| 128 | +*See [Adjusting Subtitle Position](#adjusting-subtitle-position) for tips on comfortable 3D reading.* |
| 129 | + |
| 130 | +#### Render Settings |
| 131 | + |
| 132 | +Advanced settings for the rendering engine. **Changes require a browser reload to take effect.** |
| 133 | + |
| 134 | +- **Font**: Select the UI font/language (primarily for the file explorer). |
| 135 | +- **Antialias**: Smooths jagged object outlines (aliasing). |
| 136 | +- **Super Sampling**: Increases resolution (pixel density) within VR. |
| 137 | +- **Target Frame Rate**: Sets the target FPS for WebXR (e.g., 72, 90, 120Hz). |
| 138 | +- **Video Mipmap**: Reduces flickering in distant video views using mipmapping. |
| 139 | + |
| 140 | +These settings involve a trade-off between visual fidelity and battery/performance: |
| 141 | + |
| 142 | +- **Antialias**: Can be disabled if you use `Edge Fade` to hide screen borders. |
| 143 | +- **Super Sampling**: Setting this to 1x may result in poor image quality on Meta Quest devices due to their default resolution. |
| 144 | +- **Video Mipmap**: May cause texture distortion if the screen is very small or far away; usually unneeded at standard viewing distances. |
| 145 | + |
| 146 | +##### About Fonts and Languages |
| 147 | + |
| 148 | +The iw3-player UI uses Multi-channel Signed Distance Fields (MSDF) for crisp text rendering. Using an incorrect font may prevent non-Latin characters from appearing correctly. |
| 149 | + |
| 150 | +| Font | Supported Content | |
| 151 | +| :--- | :--- | |
| 152 | +| `NotoSansJP` | Japanese (JIS Level 1 & 2) | |
| 153 | +| `NotoSansSC` | Simplified Chinese (Standard table) | |
| 154 | +| `NotoSansTC` | Traditional Chinese (MOE Standard) | |
| 155 | +| `NotoSansKR` | Korean (All Hangul syllables) | |
| 156 | +| `NotoSans` | Latin / Cyrillic (English, Russian, European, etc.) | |
| 157 | + |
| 158 | +The player automatically selects a font based on your browser's language setting. If text appears garbled, please select a font manually. |
| 159 | + |
| 160 | +*Note: Subtitles are rendered using standard browser Canvas features and are not affected by these font selections.* |
| 161 | + |
| 162 | +## Security and Privacy |
| 163 | + |
| 164 | +### Server Access |
| 165 | + |
| 166 | +The backend server starts without a password by default. |
| 167 | +It can only be accessed from within the same local network, but you can set a username and password if you feel it's necessary. |
| 168 | + |
| 169 | +### Backend Storage |
| 170 | + |
| 171 | +The backend saves thumbnails of images and videos, and subtitle data as a cache. |
| 172 | +These cannot be seen in the OS explorer, etc., but raw data is saved. |
| 173 | +There are several ways to delete it: |
| 174 | + |
| 175 | +- Delete `nunif/tmp/iw3_player_cache` |
| 176 | +- Start the backend with the `--clear-cache` option (deletes on every startup) |
| 177 | +- Access `/factory_reset.html` on the server to perform a factory reset |
| 178 | + |
| 179 | +The keys for thumbnails use a SHA256 hash value of the filename and the last modified date, and raw filenames are not saved. |
| 180 | + |
| 181 | +### Browser Storage |
| 182 | + |
| 183 | +Browser-side data is saved in IndexedDB. |
| 184 | +This includes the following data: |
| 185 | + |
| 186 | +- Global player settings |
| 187 | +- Screen settings per file |
| 188 | +- Path of the last opened file |
| 189 | + |
| 190 | +While this cannot be read by any site other than the one running on the same address:port, care is taken not to save raw filenames. |
| 191 | +In the per-file settings, the key is a SHA256 hash of the `filename + last modified date`. Raw filenames are not saved. |
| 192 | +The path of the last opened file is encrypted with AES-GCM using a key generated by the backend at first startup. It can be decrypted if the same backend is present, but cannot be decrypted with browser-side data alone. |
| 193 | + |
| 194 | +If you want to delete it, please access `/factory_reset.html` to perform a factory reset. |
| 195 | + |
| 196 | +## Screen Operation and Perception |
| 197 | + |
| 198 | +When viewing stereoscopic images, the physical adjustments made to the screen in 3D space do not always align with your psychological perception of the image. This section explains the perceptual effects of each control and recommends a workflow for the best viewing experience. |
| 199 | + |
| 200 | +### Scale |
| 201 | + |
| 202 | +The Scale setting adjusts the baseline between the left and right cameras (also known as IPD or Eye Separation). By shifting the horizontal offset, you can control the **perceived size** of objects in the scene. Use this to make people look like their actual height, or shrink them down for a "toy" effect. |
| 203 | + |
| 204 | +### Screen Size and Distance |
| 205 | + |
| 206 | +Both changing the physical screen size and changing its distance (Zoom) can be perceived as a "zoom" operation. However, iw3-player is designed to use **Distance** as the primary method for zooming. |
| 207 | + |
| 208 | +The **Screen Size** control should be used as a secondary adjustment when you reach the limits of other settings: |
| 209 | + |
| 210 | +1. Use **Distance** for standard zooming. |
| 211 | +2. Use **Screen Size** (Increase) if you want to get closer than the minimum distance. |
| 212 | +3. Use **Screen Size** (Decrease) if you want to make objects smaller than the minimum scale allows. |
| 213 | + |
| 214 | +### Perceived Depth and Volume |
| 215 | + |
| 216 | +The "thickness" or 3D volume of objects is affected by several factors: |
| 217 | + |
| 218 | +1. **Distance**: Objects appear flatter as the screen moves closer. |
| 219 | +2. **Scale**: Objects appear flatter as the scale is decreased. |
| 220 | +3. **Disparity**: Objects appear flatter if the original media has low 3D strength. |
| 221 | + |
| 222 | +The 3D strength is specified during 3D conversion in **iw3**. On iw3-player, only the Distance and Scale can be adjusted. |
| 223 | + |
| 224 | +### Recommended Workflow for Immersive Viewing |
| 225 | + |
| 226 | +To make a scene feel "real," adjust your settings in this order: |
| 227 | + |
| 228 | +1. If people look too small: **Increase Scale**. |
| 229 | +2. If people look too large: **Decrease Scale**. |
| 230 | +3. If people look too thin (flat): **Increase Distance**. |
| 231 | +4. If the depth is comfortable: You can **Decrease Distance** for more impact. |
| 232 | +5. If subjects are still too large at minimum scale: **Decrease Screen Size**. |
| 233 | +6. If subjects are still too far at minimum distance: **Increase Screen Size**. |
| 234 | + |
| 235 | +With practice, you can achieve perfect life-size immersion in seconds using just one hand. |
| 236 | + |
| 237 | +## Adjusting Subtitle Position |
| 238 | + |
| 239 | +Reading soft subtitles in 3D video can be challenging due to conflicting visual cues. This difficulty arises from the mixture of two types of disparity: |
| 240 | + |
| 241 | +1. **Simulated disparity**: Created by the difference between the left and right media tracks (the source 3D effect + the `Scale` setting). |
| 242 | +2. **Positional disparity**: Created by the physical placement of the subtitle panel in the 3D VR space. |
| 243 | + |
| 244 | +Standard 3D subtitles only have positional disparity, while the video has both. |
| 245 | +To solve this, use the **Eye Separation** setting in the Subtitle menu to add simulated disparity to the text. Adjust the subtitles so they appear to float slightly in front of the video plane for the most comfortable reading experience. |
| 246 | + |
| 247 | +## About the Development Environment |
| 248 | + |
| 249 | +iw3-player was developed through the chat interface of [gemini-cli](https://github.com/google-gemini/gemini-cli). More than 99% of the backend and frontend code was written by Gemini based on detailed specifications and iterative feedback. |
| 250 | + |
| 251 | +The initial development spanned approximately two weeks with a cost of about $100 in Gemini API Key (Tier 1) usage. |
| 252 | + |
| 253 | +### How to build vendor.bundle.js |
| 254 | + |
| 255 | +iw3-player is developed with vanilla JavaScript, but because the dependencies for `@pmndrs/uikit` are complex, external libraries are bundled using npm. |
| 256 | +Normally, pre-built files are downloaded automatically, but you can build them manually using the following commands: |
| 257 | + |
| 258 | +```bash |
| 259 | +npm install |
| 260 | +npm run build |
| 261 | +``` |
| 262 | + |
| 263 | +The output file will be generated in `public/lib`. |
| 264 | + |
| 265 | +### Dependency on `nunif` |
| 266 | + |
| 267 | +The core backend (CLI) and frontend do not strictly depend on the `nunif` framework. They can operate standalone by configuring `dir_config.py`. |
| 268 | + |
| 269 | +However, the GUI and certain other utility scripts are integrated with and dependent on `nunif`. |
0 commit comments