Correção de escala de aplicativos baseados em java para uma tela de alta DPI

23

Existem alguns aplicativos (principalmente baseados em java) que não seguem a escala global 2x que eu configurei na tela -definições. Então, esses aplicativos são realmente minúsculos na minha tela de alta DPI com 3200x1800px.

Como posso obter esses aplicativos em uma resolução de tela menor?

    
por rubo77 20.09.2014 / 23:04

3 respostas

14

Uma grande conveniência seria usar um script de plano de fundo, definindo automaticamente a resolução por aplicativo , enquanto você pode definir diferentes resoluções para diferentes (múltiplas) aplicações de uma só vez.

Isso é exatamente o que o script abaixo faz.

Um exemplo de uma resolução padrão de 1680x1050 :

Executandogedit,alterandoautomaticamentepara640x480:

Executando gnome-terminal , alterando automaticamente para 1280x1024 :

Quandooaplicativoéfechado,aresoluçãoéautomaticamentedefinidapara1680x1050

Comousar

  1. Copieoscriptabaixoemumarquivovazio,salve-ocomoset_resolution.py
  2. Nacabeçadoscript,definasuaresoluçãopadrão,nalinha:

    #---setthedefaultresolutionbelowdefault="1680x1050"
    #---
    
  3. Em o mesmo diretório (pasta), crie um arquivo de texto, exatamente chamado: procsdata.txt . Neste arquivo de texto, defina o aplicativo ou processo desejado, seguido por um espaço, seguido pela resolução desejada. Um aplicativo ou script por linha, parecido com:

    gedit 640x480
    gnome-terminal 1280x1024
    java 1280x1024
    

  4. Executeoscriptpelocomando:

    python3/path/to/set_resolution.py

Nota

Oscriptusapgrep-f<process>,quecapturatodasascorrespondências,incluindoscripts.Adesvantagempossíveléqueelepodecausarconflitosdenomeaoabrirumarquivocomomesmonomedoprocesso.
Sevocêtiverproblemascomoesse,altere:

matches.append([p,subprocess.check_output(["pgrep", "-f", p]).decode("utf-8")])

em:

matches.append([p, subprocess.check_output(["pgrep", p]).decode("utf-8")])

O script

#!/usr/bin/env python3
import subprocess
import os
import time

#--- set the default resolution below
default = "1680x1050"
#---

# read the datafile
curr_dir = os.path.dirname(os.path.abspath(__file__))
datafile = curr_dir+"/procsdata.txt"
procs_data = [l.split() for l in open(datafile).read().splitlines() if not l == "\n"]
procs = [pdata[0] for pdata in procs_data]

def check_matches():
    # function to find possible running (listed) applications
    matches = []
    for p in procs:
        try:
            matches.append([p, subprocess.check_output(["pgrep", "-f", p]).decode("utf-8")])
        except subprocess.CalledProcessError:
            pass
    match = matches[-1][0] if len(matches) != 0 else None
    return match

matches1 = check_matches()

while True:
    time.sleep(2)
    matches2 = check_matches()
    if matches2 == matches1:
        pass
    else:
        if matches2 != None:
            # a listed application started up since two seconds ago
            resdata = [("x").join(item[1].split("x")) for item in \
                       procs_data if item[0] == matches2][0]
        elif matches2 == None:
            # none of the listed applications is running any more
            resdata = default
        subprocess.Popen(["xrandr", "-s", resdata])
    matches1 = matches2
    time.sleep(1)

Explicação

Quando o script é iniciado, ele lê o arquivo no qual você definiu seus aplicativos e suas respectivas resoluções de tela desejadas.

Em seguida, ele fica de olho nos processos em execução (executando pgrep -f <process> para cada um dos aplicativos) e define a resolução se o aplicativo for iniciado.

Quando pgrep -f <process> não produz saída para nenhum dos aplicativos listados, ela define a resolução como "padrão".

Editar:

Versão "dinâmica" (conforme solicitado)

Embora a versão acima funcione com vários aplicativos listados, ela só define a resolução para um aplicativo por vez .

A versão abaixo pode lidar com diferentes aplicativos com uma resolução diferente (necessária), sendo executada ao mesmo tempo. O script de plano de fundo acompanhará o que é o aplicativo mais avançado e definirá a resolução de acordo. Ele também funciona bem com Alt + Tab .

Observe que esse comportamento pode ser chato se você alternar muito entre a área de trabalho e os aplicativos listados; o freqüente interruptor de resolução pode ser demais.

diferenças em como configurar

A configuração é praticamente a mesma, aparte do fato de que este usa wmctrl e xdotool :

sudo apt-get install wmctrl
sudo apt-get install xdotool

O script

#!/usr/bin/env python3
import subprocess
import os
import sys
import time

#--- set default resolution below
resolution = "1680x1050"
#---

curr_dir = os.path.dirname(os.path.abspath(__file__))
datafile = curr_dir+"/procsdata.txt"
applist = [l.split() for l in open(datafile).read().splitlines()]
apps = [item[0] for item in applist]

def get(cmd):
    try:
        return subprocess.check_output(["/bin/bash", "-c", cmd]).decode("utf-8")
    except subprocess.CalledProcessError:
        pass

def get_pids():
    # returns pids of listed applications; seems ok
    runs = []
    for item in apps:
        pid = get("pgrep -f "+item)
        if pid != None:
            runs.append((item, pid.strip()))    
    return runs

def check_frontmost():
    # returns data on the frontmost window; seems ok
    frontmost = str(hex(int(get("xdotool getwindowfocus").strip())))
    frontmost = frontmost[:2]+"0"+frontmost[2:]
    try:
        wlist = get("wmctrl -lpG").splitlines()
        return [l for l in wlist if frontmost in l]
    except subprocess.CalledProcessError:
        pass

def front_pid():
    # returns the frontmost pid, seems ok
    return check_frontmost()[0].split()[2]

def matching():
    # nakijken
    running = get_pids(); frontmost = check_frontmost()
    if all([frontmost != None, len(running) != 0]):
        matches = [item[0] for item in running if item[1] == frontmost[0].split()[2]]
        if len(matches) != 0:
            return matches[0]
    else:
        pass

trigger1 = matching()

while True:
    time.sleep(1)
    trigger2 = matching()
    if trigger2 != trigger1:
        if trigger2 == None:
            command = "xrandr -s "+resolution
        else:
            command = "xrandr -s "+[it[1] for it in applist if it[0] == trigger2][0]
        subprocess.Popen(["/bin/bash", "-c", command])
        print(trigger2, command)
    trigger1 = trigger2

Notas

  • Embora eu tenha executado por várias horas sem um erro agora, por favor, teste-o completamente. Se ocorrer um erro, por favor deixe um comentário.
  • O script, como é, funciona em uma única configuração de monitor.
por Jacob Vlijm 29.04.2015 / 11:12
2

Como solução alternativa

Eu criei um script bash que altera a resolução para fullHD antes de iniciar o aplicativo (neste exame do Android Studio) e o altera para 3200x1800 quando o aplicativo é encerrado:

sudo nano /usr/local/bin/studio

Digite este script:

#!/bin/bash
# set scaling to x1.0
gsettings set org.gnome.desktop.interface scaling-factor 1
gsettings set com.ubuntu.user-interface scale-factor "{'HDMI1': 8, 'eDP1': 8}"
xrandr -s 1920x1080
# call your program
/usr/share/android-studio/data/bin/studio.sh
# set scaling to x2.0
gsettings set org.gnome.desktop.interface scaling-factor 2
gsettings set com.ubuntu.user-interface scale-factor "{'HDMI1': 8, 'eDP1': 16}"
xrandr -s 3200x1800

e dê a ele direitos executáveis:

sudo chmod +x /usr/local/bin/studio

Então você pode iniciá-lo com Alt + F1 studio

Para outros fatores de redimensionamento, consulte 2.0 link

Para facilitar a troca de zoom no Firefox, use a extensão Zoom Menu Elements

    
por rubo77 20.09.2014 / 23:04
1

Teste adicionando à sua linha de comando java: -Dsun.java2d.uiScale=2.0 ou defina-o como um fator de escala que você deseja.

    
por 12.12.2018 / 03:54