Um remake de pintura baseado na Web, baseado em pixels e mais ... experimente! Em seguida, junte -se ao servidor Discord para compartilhar sua arte!
A JS Paint recria todas as ferramentas e cardápios da MS Paint e até recursos pouco conhecidos, com um alto grau de fidelidade.
Ele suporta temas, tipos de arquivos adicionais e recursos de acessibilidade, como modo de olhar ocular e reconhecimento de fala.
Ah sim, boa tinta velha. Não é aquele com as fitas ou o novo skeuomórfico com a interface que pode ocupar quase metade da tela. (E não a tinta ainda mais recente 3D.)
Windows 95, 98 e XP foram os anos dourados de tinta. Você tinha uma caixa de ferramentas e uma caixa de cores, uma cor de primeiro plano e uma cor de fundo, e isso era tudo o que você precisava.
As coisas eram simples.
Mas queremos desfazer mais de três ações. Queremos editar imagens transparentes. Não podemos simplesmente continuar usando a tinta velha.
É por isso que estou fazendo JS pintar. Eu quero trazer uma boa tinta velha para a era moderna.
Recursos de edição:
Melhorias diversas:
Algumas coisas com as ferramentas ainda não foram feitas. Veja TODO.MD
O suporte completo à área de transferência no aplicativo da web requer um navegador que suporta a API de quadro de transferência assíncrona com imagens, a saber, o Chrome 76+ no momento da redação.
Em outros navegadores, você ainda pode copiar com Ctrl+C , cortar com Ctrl+X e colar com Ctrl+V , mas os dados copiados da tinta JS só podem ser colados em outras instâncias de tinta JS. Imagens externas podem ser coladas.
Diferentemente da MS Paint, você pode usar Editar> Desfazer para reverter a redução de cor ou qualidade da economia. Isso não desfaz o salvamento do arquivo, mas permite que você salve em um formato diferente com maior qualidade, usando o arquivo> salvar como .
A economia como PNG é recomendada, pois fornece tamanhos de arquivo pequenos, mantendo a qualidade total.
Extensão de arquivo | Nome | Ler | Escrever | Leia a paleta | Escreva paleta |
---|---|---|---|---|---|
.png | Png | ✅ | ✅ | ||
.bmp, .dib | Bitmap monocromático | ✅ | ✅ | ✅ | |
.bmp, .dib | 16 colorido bitmap | ✅ | ✅ | ✅ | |
.bmp, .dib | 256 Bitmap colorido | ✅ | ✅ | ✅ | |
.bmp, .dib | Bitmap de 24 bits | ✅ | ✅ | N / D | N / D |
.tif, .tiff, .dng, .cr2, .nef | TIFF (carrega a primeira página) | ✅ | ✅ | ||
PDF (carrega a primeira página) | ✅ | ||||
.Webp | Webp | ||||
.gif | Gif | ||||
.jpeg, .jpg | JPEG | N / D | N / D | ||
.svg | SVG (apenas tamanho padrão) | ||||
.ico | OIC (apenas tamanho padrão) |
Atualmente, os recursos marcados são deixados no navegador para apoiar ou não. Se "Write" estiver marcado, o formato aparecerá no suspensão do tipo de arquivo, mas pode não funcionar quando você tentar salvar. Para abrir arquivos, consulte a tabela de suporte ao formato de imagem do navegador da Wikipedia para obter mais informações.
Os recursos marcados podem estar chegando em breve e N/A Means não aplicáveis.
"Read Palette" refere -se ao carregamento das cores na caixa de cores automaticamente (de uma imagem colorida indexada), e "Write Palette" refere -se a escrever uma imagem colorida indexada.
Com cores> Salvar cores e cores> Obtenha cores, você pode salvar e carregar cores em muitos formatos diferentes, para compatibilidade com uma ampla gama de programas.
Se você deseja adicionar um amplo suporte à paleta a outro aplicativo, disponibilizei essa funcionalidade como biblioteca: AnyPalette.js
Extensão de arquivo | Nome | Programas | Ler | Escrever |
---|---|---|---|---|
.amigo | Paleta de riff | MS Paint for Windows 95 e Windows NT 4.0 | ✅ | ✅ |
.gpl | Paleta de Gimp | Gimp, Inkscape, Krita, Kolourpaint, Scribus, Cinepaint, MyPaint | ✅ | ✅ |
.aco | Swatch de cores da Adobe | Adobe Photoshop | ✅ | ✅ |
.ea | Adobe Swatch Exchange | Adobe Photoshop, Indesign e Illustrator | ✅ | ✅ |
.TXT | PALETA DE PANTRO.NET | Tinta.net | ✅ | ✅ |
.agir | Tabela de cores do Adobe | Adobe Photoshop e Illustrator | ✅ | ✅ |
.pal, .psppalette | Paint Shop Pro Palette | Paint Shop Pro (JASC Software / Corel) | ✅ | ✅ |
.hpl | Paleta Homesite | Allaire Homesite / Macromedia Coldfusion | ✅ | ✅ |
.cs | ColorsChemer | ColorsChemer Studio | ✅ | |
.amigo | Paleta Starcraft | StarCraft | ✅ | ✅ |
.wpe | Starcraft Terrain Palette | StarCraft | ✅ | ✅ |
.SketchPalette | Paleta de esboço | Esboço | ✅ | ✅ |
.spl | Paleta de Skncil | Skncil (anteriormente chamado Sketch) | ✅ | ✅ |
.soc | Cores de ftaroffice | Staroffice, OpenOffice, LibreOffice | ✅ | ✅ |
.Colors | Coleção de cores Kolourpaint | Kolourpaint | ✅ | ✅ |
.Colors | Esquema de cores para desktop de plasma | Desktop de plasma KDE | ✅ | |
.tema | Tema do Windows | Windows Desktop | ✅ | |
.THEMEPACK | Tema do Windows | Windows Desktop | ✅ | |
.css, .scss, .styl | Folhas de estilo em cascata | Navegadores da web / páginas da web | ✅ | ✅ |
.html, .svg, .js | Qualquer arquivo de texto com cores CSS | Navegadores da web / páginas da web | ✅ |
Há um modo preto e branco com padrões em vez de cores na paleta, que você pode obter da imagem> Atributos ...
Você pode arrastar a caixa de cores e a caixa de ferramentas se você os agarrar no lugar certo. Você pode até arrastá -los para pequenas janelas. Você pode atracar as janelas de volta ao lado clicando duas vezes nas barras de título.
Além da cor de primeiro plano do clique com o botão esquerdo e da cor de fundo do clique com o botão direito do mouse, há uma terceira cor que você pode acessar mantendo o CTRL enquanto desenha. Começa sem cor, então você precisará segurar o Ctrl e selecionar uma cor primeiro. A coisa sofisticada sobre esse slot de cores é que você pode pressionar e liberar Ctrl para trocar de cor durante o desenho .
Você pode aplicar transformações de imagem como flip/girar, esticar/inclinar ou inverter (no menu de imagem) para toda a imagem ou para uma seleção. Tente rabiscar com a ferramenta de seleção de forma livre e depois fazer a imagem> Inverter
Essas dicas e truques de um tutorial para a MS Paint também funcionam no JS Paint:
O JS Paint pode ser instalado como um aplicativo da Web Progressive (PWA), embora ainda não funcione offline. Procure o prompt de instalação na barra de endereço.
Recursos PWA:
Recursos ausentes:
Também o construí em um aplicativo de desktop com elétrons e elétrons. Você pode baixá -lo na página de lançamentos.
Recursos do aplicativo Electron:
jspaint path/to/file.png
no terminaleditor_window.on("close")
chamando preventDefault
e pode ser um recurso, mas precisa mostrar/focar a janelaClone o repo.
Instale o Node.js Se você não o tiver, abra um prompt de comando / terminal no diretório do projeto.
Execute npm run lint
para verificar erros de ortografia, erros de tipo, problemas de estilo de código e outros problemas.
Execute npm run format
para corrigir automaticamente problemas de formatação ou npx eslint --fix
para corrigir todos os problemas de fixação automática.
As regras de formatação são configuradas para compatibilidade com o formatador interno do VS Code.
Execute npm test
para executar testes baseados em navegador com o CYPRESS. (É lento iniciar e executar testes, infelizmente.)
Execute npm run accept
aceitar quaisquer alterações visuais. Infelizmente, isso re-executa todos os testes, em vez de aceitar os resultados do teste anterior, para que você possa acabar com resultados diferentes do teste anterior. Se você usar o GitHub Desktop, poderá visualizar diferentes imagens, em quatro modos diferentes.
Para abrir a interface do usuário do Cypress, primeiro execute npm run test:start-server
e, em seguida, simultaneamente npm run cy:open
Os testes também são executados em integração contínua com o Travis CI.
Depois de instalar dependências com npm i
, use npm run dev
para iniciar um servidor de reloalização ao vivo.
Verifique se os estilos importantes do layout vêm no layout.css
. Ao atualizar layout.css
, uma versão da direita para a esquerda da folha de estilo é gerada, usando o RTLCSS.
Você deve testar o layout RTL alterando o idioma para árabe ou hebraico. Vá para extras> Idioma> العرaste ou עברית .
Consulte as diretivas de controle sobre como controlar o layout RTL.
Existe uma tarefa de lançamento de código VS para anexar ao Chrome para depuração. Veja .vscode/launch.json
para obter instruções de uso.
npm i
npm run electron:start
O elétron-debug está incluído, para que você possa usar F5 / Ctrl+R para recarregar e F12 / Ctrl+Shift+I para abrir os Devtools.
Você pode construir para produção com npm run electron:make
Existe uma tarefa de lançamento de código VS para depurar o processo principal de elétrons. Para o processo de renderização, você pode usar o Chrome Devtools incorporado.
A tinta JS pode ser implantada usando um servidor da web regular.
Nada precisa ser compilado.
Opcionalmente, você pode configurar um servidor CORS em qualquer lugar, para carregar imagens da web, se você colar um URL na tinta js ou usar o recurso #load:<URL>
com imagens que não estão no mesmo domínio.
Por padrão, ele usará uma instância CORS em qualquer lugar configurada para trabalhar com o jspaint.app.
Ele é hospedado gratuitamente no Heroku e você pode configurar sua própria instância e configurá -la para trabalhar com seu próprio domínio.
Você terá que encontrar e substituir https://jspaint-cors-proxy.herokuapp.com
por sua própria instância URL.
Atualmente, o suporte a multiplayer depende da Firebase, que não é um software de código aberto.
Você pode criar uma instância de banco de dados em tempo initializeApp
do Firebase e editar config
sessions.js
da JS Paint.
Mas o modo multiplayer é muito ruim até agora. Ele deve ser substituído por algo de código aberto, mais seguro, mais eficiente e mais robusto.
Adicione isso ao seu HTML:
< iframe src =" https://jspaint.app " width =" 100% " height =" 100% " > </ iframe >
Você pode carregar uma imagem de um URL adicionando #load:<URL>
ao URL.
< iframe src =" https://jspaint.app#load:https://jspaint.app/favicon.ico " width =" 100% " height =" 100% " > </ iframe >
Se você deseja controlar o JS Paint, como ela salva/carrega arquivos ou acessar a tela diretamente, há uma API instável.
Primeiro, você precisa clonar o repositório, para poder apontar um iframe
para a cópia local.
A cópia local do JS Paint deve ser hospedada no mesmo servidor da web que a página contendo, ou mais especificamente, deve compartilhar a mesma origem.
Ter uma cópia local também significa que as coisas não quebram a qualquer momento, a API muda.
Se a tinta js for clonada para uma pasta chamada jspaint
, que vive na mesma pasta da página em que você deseja incorporá -la, você pode usar isso:
< iframe src =" jspaint/index.html " id =" jspaint-iframe " width =" 100% " height =" 100% " > </ iframe >
Se mora em outro lugar, pode ser necessário adicionar ../
ao início do caminho, subir um nível. Por exemplo, src="../../apps/jspaint/index.html"
. Você também pode usar um URL absoluto, como src="https://example.com/cool-apps/jspaint/index.html"
.
Você pode substituir as caixas de diálogo Salvando e abrindo de arquivo com a API systemHooks
da JS Paint.
< script >
var iframe = document . getElementById ( "jspaint-iframe" ) ;
var jspaint = iframe . contentWindow ;
// Wait for systemHooks object to exist (the iframe needs to load)
waitUntil ( ( ) => jspaint . systemHooks , 500 , ( ) => {
// Hook in
jspaint . systemHooks . showSaveFileDialog = async ( { formats , defaultFileName , defaultPath , defaultFileFormatID , getBlob , savedCallbackUnreliable , dialogTitle } ) => { ... } ;
jspaint . systemHooks . showOpenFileDialog = async ( { formats } ) => { ... } ;
jspaint . systemHooks . writeBlobToHandle = async ( save_file_handle , blob ) => { ... } ;
jspaint . systemHooks . readBlobFromHandle = async ( file_handle ) => { ... } ;
} ) ;
// General function to wait for a condition to be met, checking at regular intervals
function waitUntil ( test , interval , callback ) {
if ( test ( ) ) {
callback ( ) ;
} else {
setTimeout ( waitUntil , interval , test , interval , callback ) ;
}
}
</ script >
Um blob representa o conteúdo de um arquivo na memória.
Um identificador de arquivo é qualquer coisa que possa identificar um arquivo. Você possui esse conceito e define como identificar arquivos. Pode ser qualquer coisa, desde um índice em uma matriz, até um ID do arquivo do Dropbox, até um URL do IPFS, até um caminho de arquivo. Pode ser qualquer tipo, ou talvez precise ser uma corda, eu esqueço.
Depois de ter um conceito de identificação de arquivo, você pode implementar os seleiros de arquivos usando os ganchos do sistema e funções para ler e gravar arquivos.
Comando | Ganchos usados |
---|---|
Arquivo> Salvar como | systemHooks.showSaveFileDialog , então quando um arquivo é escolhido, systemHooks.writeBlobToHandle |
Arquivo> Abrir | systemHooks.showOpenFileDialog , então quando um arquivo é escolhido, systemHooks.readBlobFromHandle |
Arquivo> Salvar | systemHooks.writeBlobToHandle (ou o mesmo que o arquivo> Salvar como se ainda não houvesse arquivo aberto) |
Editar> Copiar para | systemHooks.showSaveFileDialog , então quando um arquivo é escolhido, systemHooks.writeBlobToHandle |
Editar> Colar de | systemHooks.showOpenFileDialog , então quando um arquivo é escolhido, systemHooks.readBlobFromHandle |
Arquivo> Definido como papel de parede (azulejo) | systemHooks.setWallpaperTiled , se definido, else systemHooks.setWallpaperCentered , se definido, caso contrário, o arquivo> salvar como |
Arquivo> definido como papel de parede (centrado) | systemHooks.setWallpaperCentered se definido, caso contrário, o arquivo> salvar como |
Extras> renderizar história como gif | O mesmo que o arquivo> salvar como |
Cores> Salvar cores | O mesmo que o arquivo> salvar como |
Cores> Obtenha cores | O mesmo que o arquivo> aberto |
Para iniciar o aplicativo com um arquivo carregado para edição, aguarde o carregamento do aplicativo e ligue para systemHooks.readBlobFromHandle
com um identificador de arquivo e diga ao aplicativo para carregar esse blob de arquivo.
const file_handle = "initial-file-to-load" ;
systemHooks . readBlobFromHandle ( file_handle ) . then ( file => {
if ( file ) {
contentWindow . open_from_file ( file , file_handle ) ;
}
} , ( error ) => {
// Note: in some cases, this handler may not be called, and instead an error message is shown by readBlobFromHandle directly.
contentWindow . show_error_message ( `Failed to open file ${ file_handle } ` , error ) ;
} ) ;
Isso é desajeitado e, no futuro, pode haver um parâmetro de sequência de consulta para carregar um arquivo inicial por seu identificador. (Nota para si mesmo: ele precisará esperar que seus ganchos do sistema sejam registrados, de alguma forma.)
Já existe um parâmetro de sequência de consulta para carregar de um URL:
< iframe src =" https://jspaint.app?load:SOME_URL_HERE " > </ iframe >
Mas isso não configurará o identificador de arquivo para salvar.
Você pode definir duas funções para definir o papel de parede, que será usado por arquivo> definido como papel de parede (ladrilho) e arquivo> definido como papel de parede (centrado) .
systemHooks.setWallpaperTiled
= (canvas) => { ... };
systemHooks.setWallpaperCentered
= (canvas) => { ... };
Se você definir apenas systemHooks.setWallpaperCentered
, o JS Paint tentará adivinhar as dimensões da tela e ladrilho a imagem, aplicando -a chamando seu systemHooks.setWallpaperCentered
Função.
Se você não especificar systemHooks.setWallpaperCentered
, o JS Paint padrão para salvar um arquivo ( <original file name> wallpaper.png
) usando systemHooks.showSaveFileDialog
e systemHooks.writeBlobToHandle
.
Aqui está um exemplo completo que suporta um papel de parede personalizado persistente como plano de fundo na página contendo:
const wallpaper = document . querySelector ( "body" ) ; // or some other element
jspaint . systemHooks . setWallpaperCentered = ( canvas ) => {
canvas . toBlob ( ( blob ) => {
setDesktopWallpaper ( blob , "no-repeat" , true ) ;
} ) ;
} ;
jspaint . systemHooks . setWallpaperTiled = ( canvas ) => {
canvas . toBlob ( ( blob ) => {
setDesktopWallpaper ( blob , "repeat" , true ) ;
} ) ;
} ;
function setDesktopWallpaper ( file , repeat , saveToLocalStorage ) {
const blob_url = URL . createObjectURL ( file ) ;
wallpaper . style . backgroundImage = `url( ${ blob_url } )` ;
wallpaper . style . backgroundRepeat = repeat ;
wallpaper . style . backgroundPosition = "center" ;
wallpaper . style . backgroundSize = "auto" ;
if ( saveToLocalStorage ) {
const fileReader = new FileReader ( ) ;
fileReader . onload = ( ) => {
localStorage . setItem ( "wallpaper-data-url" , fileReader . result ) ;
localStorage . setItem ( "wallpaper-repeat" , repeat ) ;
} ;
fileReader . onerror = ( ) => {
console . error ( "Error reading file (for setting wallpaper)" , file ) ;
} ;
fileReader . readAsDataURL ( file ) ;
}
}
// Initialize the wallpaper from localStorage, if it exists
try {
const wallpaper_data_url = localStorage . getItem ( "wallpaper-data-url" ) ;
const wallpaper_repeat = localStorage . getItem ( "wallpaper-repeat" ) ;
if ( wallpaper_data_url ) {
fetch ( wallpaper_data_url ) . then ( response => response . blob ( ) ) . then ( file => {
setDesktopWallpaper ( file , wallpaper_repeat , false ) ;
} ) ;
}
} catch ( error ) {
console . error ( error ) ;
}
É um pouco recursivo, desculpe; Provavelmente poderia ser feito mais simples. Como apenas usando URLs de dados. (Na verdade, acho que queria usar URLs de blob apenas para que não incha o inspetor DOM com um URL super longo. O que é realmente um bug de Devtools UX. Talvez eles tenham melhorado isso?)
Você pode carregar um arquivo que possui as dimensões desejadas. Não há API especial para isso no momento.
Consulte Carregando um arquivo inicialmente.
Você pode mudar o tema programaticamente:
var iframe = document . getElementById ( "jspaint-iframe" ) ;
var jspaint = iframe . contentWindow ;
jspaint . set_theme ( "modern.css" ) ;
Mas isso quebrará a preferência do usuário.
O menu de temas extras> ainda funcionará, mas a preferência não persistirá ao recarregar a página.
No futuro, pode haver um parâmetro de sequência de consulta para especificar o tema padrão. Você também pode bifurcar o JSPAINT para alterar o tema padrão.
Semelhante ao tema, você pode tentar alterar a linguagem programaticamente:
var iframe = document . getElementById ( "jspaint-iframe" ) ;
var jspaint = iframe . contentWindow ;
jspaint . set_language ( "ar" ) ;
Mas isso realmente solicitará ao usuário que recarregue o aplicativo para alterar os idiomas.
O menu de idiomas extras> ainda funcionará, mas o usuário se preocupará em alterar o idioma toda vez que recarregue a página.
No futuro, pode haver um parâmetro de sequência de consulta para especificar o idioma padrão. Você também pode gastar Jspaint para alterar o idioma padrão.
Ainda não suportado. Você pode bifurcar Jspaint e adicionar seus próprios menus.
Com acesso à tela, você pode implementar uma prévia ao vivo do seu desenho, por exemplo, atualizando uma textura em um mecanismo de jogo em tempo real.
var iframe = document . getElementById ( "jspaint-iframe" ) ;
// contentDocument here refers to the webpage loaded in the iframe, not the image document loaded in jspaint.
// We're just reaching inside the iframe to get the canvas.
var canvas = iframe . contentDocument . querySelector ( ".main-canvas" ) ;
É recomendável não usar isso para carregar um documento, pois ele não alterará o título do documento ou redefinirá o histórico de desfazer/refazer, entre outras coisas. Em vez disso, use open_from_file
.
Se você quiser fazer botões ou outra interface do usuário para fazer as coisas no documento, você deve (provavelmente) torná -lo ilegal. É muito fácil, basta envolver sua ação em um chamado para undoable
.
var iframe = document . getElementById ( "jspaint-iframe" ) ;
var jspaint = iframe . contentWindow ;
var icon = new Image ( ) ;
icon . src = "some-folder/some-image-15x11-pixels.png" ;
jspaint . undoable ( {
name : "Seam Carve" ,
icon : icon , // optional
} , function ( ) {
// do something to the canvas
} ) ;
systemHooks.showSaveFileDialog({ formats, defaultFileName, defaultPath, defaultFileFormatID, getBlob, savedCallbackUnreliable, dialogTitle })
Defina esta função para substituir a caixa de diálogo Salvar padrão. Isso é usado para salvar imagens, bem como arquivos de paleta e animações.
Argumentos:
formats
: Uma variedade de objetos que representam tipos de arquivos, com as seguintes propriedades:formatID
: uma string que identifica exclusivamente o formato (pode ser o mesmo que mimeType
)mimeType
(Opcional): o tipo de mídia designado do formato do arquivo, por exemplo "image/png"
(os formatos de paleta não têm essa propriedade)name
: o nome do formato do arquivo, por exemplo "WebP"
nameWithExtensions
: o nome do formato do arquivo seguido de uma lista de extensões, por exemplo, "TIFF (*.tif;*.tiff)"
extensions
: uma matriz de extensões de arquivo, excluindo o ponto, com a extensão preferida primeiro, por exemplo, ["bmp", "dib"]
defaultFileName
(Opcional): um nome de arquivo sugerido, por exemplo, "Untitled.png"
ou o nome de um documento aberto.defaultPath
(Opcional): um identificador de arquivo para um documento que foi aberto, para que você possa salvar na mesma pasta facilmente. Menço: isso pode não ser um caminho, depende de como você define as alças de arquivo.defaultFileFormatID
(Opcional): o formatID
de um formato de arquivo a ser selecionado por padrão.async function getBlob(formatID)
: uma função que você chama para obter um arquivo em um dos formatos suportados. É preciso uma formatID
e retorna uma Promise
que resolve com um Blob
representando o conteúdo do arquivo para salvar.function savedCallbackUnreliable({ newFileName, newFileFormatID, newFileHandle, newBlob })
(opcional): uma função que você chama quando o usuário salvar o arquivo. O newBlob
deve vir do getBlob(newFileFormatID)
.dialogTitle
(Opcional): um título para a caixa de diálogo Salvar. Observe a inversão do controle aqui: o JS Paint chama sua função systemHooks.showSaveFileDialog
e, em seguida, você chama a função getBlob
da JS Paint. Depois que getBlob
resolver, você pode chamar a função savedCallbackUnreliable
, que é definida pela JS Paint. (Espero poder esclarecer isso no futuro.)
Observe também que esta função é responsável por salvar o arquivo, não apenas escolhendo um local de salvamento. Você pode reutilizar sua função systemHooks.writeBlobToHandle
, se for útil.
systemHooks.showOpenFileDialog({ formats })
Defina essa função para substituir a caixa de diálogo aberta padrão. Isso é usado para abrir imagens e paletas.
Argumentos:
formats
: o mesmo que systemHooks.showSaveFileDialog
Observe que esta função é responsável por carregar o conteúdo do arquivo, não apenas escolhendo um arquivo. Você pode reutilizar sua função systemHooks.readBlobFromHandle
, se for útil.
systemHooks.writeBlobToHandle(fileHandle, blob)
Defina essa função para informar a JS Paint como salvar um arquivo.
Argumentos:
fileHandle
: um identificador de arquivo, conforme definido pelo seu sistema, representando o arquivo para gravar.blob
: Um Blob
representando o conteúdo do arquivo para salvar.Retornos:
Promise
que resolve com true
se o arquivo foi definitivamente salvo com sucesso, false
se ocorreu um erro ou o usuário cancelado ou undefined
se não se sabe se o arquivo foi salvo com sucesso, como é o caso do download de arquivos com <a href="..." download="...">
. A promessa não deve rejeitar; Os erros devem ser tratados mostrando uma mensagem de erro e retornando false
. systemHooks.readBlobFromHandle(fileHandle)
Defina essa função para informar a JS Paint como carregar um arquivo.
Argumentos:
fileHandle
: um identificador de arquivo, conforme definido pelo seu sistema, representando o arquivo para ler. systemHooks.setWallpaperTiled(canvas)
Defina essa função para dizer a JS Paint como definir o papel de parede. Consulte o conjunto de parede de integração como um exemplo.
Argumentos:
canvas
: um HTMLCanvasElement
com a imagem para definir como papel de parede. systemHooks.setWallpaperCentered(canvas)
Defina essa função para dizer a JS Paint como definir o papel de parede. Consulte o conjunto de parede de integração como um exemplo.
Argumentos:
canvas
: um HTMLCanvasElement
com a imagem para definir como papel de parede. undoable({ name, icon }, actionFunction)
Use isso para tornar uma ação sem preenchimento.
Essa função recebe um instantâneo da tela e algum outro estado e depois chama a função de actionFunction
. Ele cria uma entrada na história para que possa ser desfeita.
Argumentos:
name
: um nome para a ação, por exemplo "Brush"
ou "Rotate Image 270°"
icon
(opcional): uma Image
a ser exibida na janela History. Recomenda -se ser de 15x11 pixels.actionFunction
: uma função que não leva argumentos e modifica a tela. show_error_message(message, [error])
Use isso para mostrar uma caixa de diálogo de mensagem de erro, opcionalmente com detalhes de erro expansíveis.
Argumentos:
message
: Texto simples a ser exibido na caixa de diálogo.error
(Opcional): Um objeto Error
a ser exibido na caixa de diálogo, colapsado por padrão em uma seção expansível "Detalhes". open_from_file(blob, source_file_handle)
Use isso para carregar um arquivo no aplicativo.
Argumentos:
blob
: Um objeto Blob
representando o arquivo a ser carregado.source_file_handle
: um identificador de arquivo correspondente para o arquivo, conforme definido pelo seu sistema.Desculpe pela API peculiar. A API é nova e partes dela não foram projetadas. Este foi apenas um hack do qual eu vim depender, alcançando os internos do JS Paint para carregar um arquivo. Decidi documentá -lo como a primeira versão da API, já que vou querer um Changelog ao atualizar meu uso de qualquer maneira.
set_theme(theme_file_name)
Use isso para alterar a aparência do aplicativo.
Argumentos:
theme_file_name
: o nome do arquivo de tema a ser carregado, um de:"classic.css"
: o tema do Windows98."dark.css"
: o tema sombrio."modern.css"
: o tema moderno."winter.css"
: o tema festivo de inverno."occult.css"
: um tema satânico. set_language(language_code)
Você pode usar isso para alterar o idioma do aplicativo. Mas, na verdade, ele mostrará um prompt ao usuário para alterar o idioma, porque o aplicativo precisa recarregar para aplicar a alteração. E se essa caixa de diálogo não estiver no idioma certo, bem, eles provavelmente ficarão confusos.
Argumentos:
language_code
: o código do idioma a ser usado, por exemplo, "en"
para inglês, "zh"
para chinês tradicional, "zh-simplified"
para chinês simplificado, etc. A API mudará muito, mas as alterações serão documentadas no Changelog.
Não apenas um histórico de mudanças, mas um guia de migração/atualização.
Para notícias gerais do projeto, clique em Extras> Notícias do projeto no aplicativo.
O JS Paint é software gratuito e de código aberto, licenciado sob a licença permissiva do MIT.