upscale.js 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120
  1. import GObject from 'gi://GObject';
  2. import * as utils from '../conveniences/utils.js';
  3. const Shell = await utils.import_in_shell_only('gi://Shell');
  4. const Clutter = await utils.import_in_shell_only('gi://Clutter');
  5. const SHADER_FILENAME = 'upscale.glsl';
  6. const DEFAULT_PARAMS = {
  7. factor: 8, width: 0, height: 0
  8. };
  9. export const UpscaleEffect = utils.IS_IN_PREFERENCES ?
  10. { default_params: DEFAULT_PARAMS } :
  11. new GObject.registerClass({
  12. GTypeName: "UpscaleEffect",
  13. Properties: {
  14. 'factor': GObject.ParamSpec.int(
  15. `factor`,
  16. `Factor`,
  17. `Factor`,
  18. GObject.ParamFlags.READWRITE,
  19. 0, 64,
  20. 8,
  21. ),
  22. 'width': GObject.ParamSpec.double(
  23. `width`,
  24. `Width`,
  25. `Width`,
  26. GObject.ParamFlags.READWRITE,
  27. 0.0, Number.MAX_SAFE_INTEGER,
  28. 0.0,
  29. ),
  30. 'height': GObject.ParamSpec.double(
  31. `height`,
  32. `Height`,
  33. `Height`,
  34. GObject.ParamFlags.READWRITE,
  35. 0.0, Number.MAX_SAFE_INTEGER,
  36. 0.0,
  37. )
  38. }
  39. }, class UpscaleEffect extends Clutter.ShaderEffect {
  40. constructor(params) {
  41. super(params);
  42. utils.setup_params(this, params);
  43. // set shader source
  44. this._source = utils.get_shader_source(Shell, SHADER_FILENAME, import.meta.url);
  45. if (this._source)
  46. this.set_shader_source(this._source);
  47. }
  48. static get default_params() {
  49. return DEFAULT_PARAMS;
  50. }
  51. get factor() {
  52. return this._factor;
  53. }
  54. set factor(value) {
  55. if (this._factor !== value) {
  56. this._factor = value;
  57. this.set_uniform_value('factor', this._factor);
  58. }
  59. }
  60. get width() {
  61. return this._width;
  62. }
  63. set width(value) {
  64. if (this._width !== value) {
  65. this._width = value;
  66. this.set_uniform_value('width', parseFloat(this._width - 1e-6));
  67. }
  68. }
  69. get height() {
  70. return this._height;
  71. }
  72. set height(value) {
  73. if (this._height !== value) {
  74. this._height = value;
  75. this.set_uniform_value('height', parseFloat(this._height - 1e-6));
  76. }
  77. }
  78. vfunc_set_actor(actor) {
  79. if (this._actor_connection_size_id) {
  80. let old_actor = this.get_actor();
  81. old_actor?.disconnect(this._actor_connection_size_id);
  82. }
  83. if (actor) {
  84. this.width = actor.width;
  85. this.height = actor.height;
  86. this._actor_connection_size_id = actor.connect('notify::size', _ => {
  87. this.width = actor.width;
  88. this.height = actor.height;
  89. });
  90. }
  91. else
  92. this._actor_connection_size_id = null;
  93. super.vfunc_set_actor(actor);
  94. }
  95. vfunc_paint_target(paint_node, paint_context) {
  96. // force setting nearest-neighbour texture filtering
  97. this.get_pipeline().set_layer_filters(0, 9728, 9728);
  98. super.vfunc_paint_target(paint_node, paint_context);
  99. }
  100. });