/* ============================================================================== This file is part of the JUCE library. Copyright (c) 2017 - ROLI Ltd. JUCE is an open source library subject to commercial or open-source licensing. By using JUCE, you agree to the terms of both the JUCE 5 End-User License Agreement and JUCE 5 Privacy Policy (both updated and effective as of the 27th April 2017). End User License Agreement: www.juce.com/juce-5-licence Privacy Policy: www.juce.com/juce-5-privacy-policy Or: You may also use this code under the terms of the GPL v3 (see www.gnu.org/licenses). JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE DISCLAIMED. ============================================================================== */ namespace juce { // This byte-code is generated from native/java/com/roli/juce/ComponentPeerView.java with min sdk version 16 // See juce_core/native/java/README.txt on how to generate this byte-code. static const uint8 javaComponentPeerView[] = {31,139,8,8,248,105,229,91,0,3,67,111,109,112,111,110,101,110,116,80,101,101,114,86,105,101,119,46,100,101,120,0,165,154, 11,124,92,85,157,199,255,231,220,59,51,201,100,50,153,76,210,164,73,38,233,228,217,105,155,38,83,160,208,146,180,244,13, 105,147,182,52,105,160,73,129,222,76,110,146,105,39,247,78,103,38,143,10,46,225,177,148,69,228,225,118,1,5,93,68,100,171, 162,219,34,178,5,92,101,149,197,174,162,91,124,176,85,235,10,10,31,145,45,136,221,186,174,136,178,191,115,238,153,100, 250,2,117,39,159,239,252,255,231,127,254,247,188,207,255,156,153,204,160,57,233,141,158,191,152,158,156,245,224,205,149, 149,85,69,59,14,196,31,217,241,202,99,15,124,242,195,239,188,245,102,211,239,146,201,249,68,73,34,154,236,189,32,72,234, 245,232,60,162,227,228,216,23,129,176,78,116,17,228,43,144,165,194,215,67,52,4,57,59,143,72,131,188,172,128,232,112,13, 209,126,200,19,229,68,39,193,59,160,116,54,81,57,168,2,53,160,14,52,130,121,96,21,88,11,58,64,23,216,2,118,130,7,193,211, 224,69,240,107,80,92,129,54,128,237,96,28,220,9,30,6,79,129,239,129,95,129,202,74,162,86,208,1,110,0,15,129,239,130,223, 129,198,42,162,30,240,0,248,15,240,54,168,9,17,45,7,6,184,22,220,1,30,3,71,193,27,32,80,77,212,0,86,131,43,192,45,224,33, 176,31,60,1,158,4,255,12,158,5,135,193,17,240,34,56,6,94,6,175,130,215,193,175,192,73,240,54,248,35,112,99,140,242,129, 31,148,130,10,80,13,234,64,19,152,15,150,131,110,112,13,216,5,38,192,77,224,78,240,0,120,24,28,4,79,131,23,193,15,193, 113,112,18,188,3,244,57,68,133,160,20,212,130,22,176,28,116,129,94,112,21,136,129,33,48,10,174,5,183,128,143,131,71,193, 19,224,107,224,8,248,49,120,11,252,30,248,194,24,103,80,15,154,193,82,176,1,244,131,36,184,30,220,9,62,15,190,8,158,4,95, 6,223,6,63,5,191,6,84,139,182,129,122,112,1,88,11,122,128,1,118,129,155,193,29,96,31,184,23,124,10,236,7,79,130,195,224, 135,224,21,112,2,188,13,220,117,152,43,80,5,26,192,50,208,9,186,193,0,24,1,73,48,9,174,5,55,128,219,192,93,224,30,240,25, 240,21,112,4,252,28,80,61,81,9,104,2,139,193,70,208,11,76,48,6,166,192,157,224,62,240,16,56,8,190,10,190,1,142,128,31, 129,151,193,27,224,36,248,45,168,106,192,88,129,21,96,45,216,10,98,224,58,112,59,248,24,120,28,124,11,188,6,126,3,244,70, 244,11,132,65,11,88,6,186,192,118,48,14,174,3,55,131,219,193,71,192,189,224,227,224,31,192,103,193,65,240,20,120,6,188,0, 142,129,55,193,219,224,15,128,154,80,7,200,107,114,246,175,11,96,75,147,31,20,129,0,40,6,34,32,148,144,179,231,103,129, 50,80,46,246,61,192,182,35,108,47,194,118,34,108,25,194,242,38,44,63,154,35,226,133,51,213,164,134,148,208,37,82,213,210, 92,16,1,8,49,132,208,67,11,64,51,88,8,90,64,43,136,170,184,115,30,56,31,92,0,22,131,37,224,82,208,5,54,130,77,96,51,57, 125,200,190,116,37,31,44,115,250,197,84,218,173,116,97,23,125,229,202,158,167,244,253,176,123,149,159,120,249,84,222,1, 101,247,43,187,87,141,75,86,159,149,227,47,198,229,80,153,163,139,49,121,70,61,91,171,124,10,212,88,136,54,20,170,241,56, 172,252,133,126,68,249,71,148,127,161,26,163,163,101,78,223,23,40,251,82,165,139,114,46,86,250,75,208,219,148,126,28,122, 187,210,79,66,95,166,116,29,147,183,92,233,1,232,151,40,61,4,125,133,210,27,160,175,202,206,75,142,253,130,28,189,29,250, 26,165,175,201,177,111,206,209,175,204,209,119,228,148,57,146,99,79,66,95,173,244,201,28,251,93,101,51,186,24,195,149,74, 159,202,41,231,214,28,127,49,110,107,179,207,194,190,78,233,247,229,248,236,207,209,15,148,59,235,168,89,141,231,101,74, 63,4,123,135,210,159,129,190,94,233,207,67,239,84,250,247,161,111,80,250,177,28,251,43,57,246,227,229,98,78,25,93,69,142, 60,70,98,223,132,233,74,37,239,148,146,209,71,148,220,167,228,223,41,121,143,146,247,42,255,7,73,236,181,102,250,123,41, 171,232,71,36,246,93,136,126,168,228,207,164,172,164,87,197,92,98,53,223,37,101,21,125,66,202,102,250,178,148,5,244,85, 185,254,106,233,66,18,123,166,132,14,146,216,35,213,244,117,18,235,222,77,163,82,6,232,3,144,249,200,103,82,46,164,231, 72,172,203,90,153,46,80,246,2,236,162,111,200,254,57,233,34,212,155,144,178,152,44,149,190,86,172,51,101,15,96,103,238, 86,233,49,41,53,26,39,39,214,76,40,57,41,37,163,41,37,111,32,177,215,56,165,164,172,163,235,73,196,163,26,89,95,9,162, 195,19,82,46,162,127,146,114,22,61,69,98,63,54,81,159,146,207,146,136,89,141,210,191,2,145,228,14,41,235,233,155,82,46, 166,239,203,241,156,43,243,43,81,194,151,228,56,206,147,233,42,216,47,87,114,139,148,62,234,150,178,132,126,160,228,139, 114,92,231,72,255,16,70,178,71,202,8,109,149,178,132,182,43,105,72,25,37,83,202,74,218,37,165,91,222,175,66,170,127,33, 68,191,180,148,249,180,71,74,47,93,167,242,63,40,101,30,253,149,148,206,56,132,208,179,155,148,188,89,201,191,150,114,54, 221,162,228,94,101,191,85,202,114,250,27,37,111,83,242,67,82,86,208,237,82,182,210,253,74,62,32,101,136,62,171,214,209, 231,148,124,84,201,207,171,252,47,168,244,63,42,121,64,173,179,199,164,12,211,23,165,108,164,199,165,116,230,43,164,230, 75,164,15,169,245,249,164,148,206,252,133,16,237,159,150,114,1,29,86,242,223,164,108,160,231,165,44,165,239,72,57,159, 254,93,165,143,40,191,23,148,252,174,202,255,158,234,255,207,73,196,224,32,101,164,188,144,62,38,247,129,159,94,38,17, 119,157,245,219,132,104,107,147,136,189,26,13,72,201,233,83,36,226,111,17,125,148,156,179,142,200,137,211,34,62,137,51, 99,7,228,87,84,176,174,82,107,184,73,249,137,252,36,242,95,80,249,226,60,40,38,231,60,189,79,61,63,5,249,187,200,140,255, 109,208,239,142,56,231,217,253,144,15,129,71,35,206,185,245,37,105,231,206,222,107,18,251,18,119,175,96,1,37,3,6,108,65, 218,30,240,202,51,42,15,41,241,124,41,124,250,69,125,238,82,170,227,62,248,229,227,233,158,116,1,245,156,239,35,43,112, 62,188,124,44,72,75,89,251,140,53,124,17,118,199,140,207,34,248,120,181,45,56,178,182,52,50,58,216,115,55,105,250,226,29, 149,180,53,237,165,37,90,25,5,181,237,208,178,254,61,153,2,218,29,104,194,62,247,233,187,3,243,33,11,244,221,209,5,180, 218,37,252,151,106,30,186,104,135,139,130,37,226,25,63,234,42,195,92,88,129,89,104,239,233,117,68,190,35,206,113,77,142, 201,210,38,231,78,210,31,244,169,190,214,97,46,146,225,90,140,118,127,192,79,253,37,133,178,223,76,254,33,126,55,57,119, 128,100,64,220,52,252,211,246,203,167,237,17,105,231,234,102,176,77,221,129,122,2,133,114,126,52,216,69,189,70,147,115, 46,247,132,11,209,74,113,3,65,15,107,69,187,171,80,179,127,218,111,228,156,126,33,233,231,71,92,16,61,177,225,39,214,127, 208,29,156,149,12,151,211,103,168,78,23,179,231,65,171,250,247,33,186,233,85,148,140,214,211,190,252,254,125,1,10,233,46, 148,112,13,61,76,94,125,137,126,21,205,241,138,52,195,202,237,123,160,8,90,63,197,105,251,253,136,180,225,30,218,134,247, 173,242,189,23,43,181,14,43,35,25,16,61,45,209,75,169,126,229,66,106,98,34,142,89,97,23,218,211,35,106,114,121,49,126, 110,18,37,230,33,102,5,53,43,48,128,167,124,122,165,235,91,20,108,170,31,106,165,160,103,32,175,132,186,242,220,158,96, 121,40,175,64,106,86,244,106,234,113,251,180,37,90,41,5,121,176,161,126,77,148,130,174,221,129,29,232,157,207,221,229, 214,93,193,89,65,41,173,168,73,127,171,99,12,2,28,81,204,167,207,209,157,214,239,163,200,39,11,245,200,73,112,2,188,5, 126,4,142,98,202,229,29,115,230,53,117,9,253,89,233,211,95,78,190,56,191,203,16,143,76,114,206,19,174,213,223,204,234, 110,100,243,166,24,159,123,43,107,188,133,57,243,45,94,63,80,235,160,59,92,36,247,177,88,127,34,125,44,187,110,162,203, 168,86,19,179,233,236,175,87,213,186,236,94,81,68,101,92,222,87,249,82,228,248,165,37,25,189,152,116,22,121,123,166,252, 55,154,156,251,168,184,67,247,161,14,191,170,67,188,254,187,201,217,255,193,64,209,244,186,252,131,106,207,214,64,177, 172,135,171,117,204,231,58,119,68,43,176,88,236,28,220,5,117,249,92,144,34,127,212,84,121,121,115,157,152,225,151,207,57, 55,221,64,142,205,13,155,240,44,159,251,222,125,88,162,250,144,245,15,191,143,255,210,233,62,59,237,152,119,150,118,44, 58,139,109,73,142,77,87,117,93,50,215,185,55,7,153,136,188,253,81,78,142,212,104,219,34,68,145,183,182,69,61,180,45,234, 86,214,124,172,31,220,220,3,219,162,58,242,243,176,11,202,208,158,106,10,179,98,213,95,49,246,27,231,58,49,248,236,237, 239,89,21,164,228,150,149,164,95,30,249,95,241,25,65,147,243,222,123,206,103,206,95,251,238,187,178,223,43,90,73,55,196, 51,249,176,139,122,98,115,157,251,122,176,184,123,0,79,233,226,41,174,203,153,194,248,53,123,196,103,36,145,99,5,124,136, 215,216,141,155,219,168,41,205,2,145,19,118,116,54,141,231,121,41,242,134,21,136,162,221,62,220,46,52,248,137,81,66,190, 184,232,113,167,93,217,207,96,37,106,220,4,94,228,136,250,175,159,235,124,158,10,178,233,250,57,234,199,147,69,108,169, 39,31,229,121,209,86,47,15,214,159,119,158,135,236,21,21,52,126,159,151,69,78,88,129,2,17,7,248,18,254,198,187,89,221,10, 199,208,106,175,108,175,108,167,22,44,142,252,196,25,31,81,215,71,231,58,159,129,78,29,31,167,167,194,38,250,232,70,93, 201,45,237,24,217,96,32,242,27,231,174,41,94,143,228,204,123,62,74,19,229,61,174,198,219,190,178,146,122,198,115,75,93, 130,58,157,117,118,21,214,153,243,89,149,203,207,104,255,138,103,66,40,168,251,5,120,99,241,44,98,76,91,202,208,6,86,196, 172,128,56,31,188,249,86,64,196,226,2,207,15,238,126,151,22,176,255,145,163,19,249,117,247,119,177,115,152,21,14,224,86, 233,213,45,236,53,248,186,172,64,80,72,183,231,133,241,188,229,226,116,45,142,28,123,127,207,21,142,231,55,222,223,243, 18,120,90,1,17,3,188,5,193,226,139,170,230,83,176,182,62,212,130,24,121,30,125,155,130,149,139,159,170,37,81,138,40,227, 11,162,140,112,137,144,44,232,90,227,242,185,110,220,250,220,44,43,92,234,88,202,214,184,125,238,27,135,158,43,203,150, 123,212,139,153,124,9,237,184,169,148,209,187,184,55,220,253,178,151,229,45,245,206,166,63,181,7,243,104,232,221,220,246, 252,37,45,17,37,69,126,252,231,183,96,185,106,65,227,255,187,5,203,101,11,196,182,241,200,181,38,214,150,136,21,173,74, 138,24,35,238,165,105,185,246,184,60,163,47,142,56,223,65,160,141,56,17,61,88,253,149,26,230,163,180,126,13,78,68,215, 128,27,39,162,60,221,174,166,243,116,31,91,138,146,253,184,53,70,254,8,222,9,6,235,235,112,30,106,226,60,204,195,153,215, 165,115,77,156,131,187,121,228,205,66,30,57,14,94,7,175,137,245,94,140,182,137,251,162,216,25,156,207,45,107,156,173,213, 71,234,154,231,205,207,137,137,131,145,153,189,161,41,107,34,226,220,251,150,112,15,246,151,21,222,6,15,63,5,87,68,126, 47,250,231,196,205,177,136,243,157,137,136,31,226,134,87,201,239,131,167,134,88,42,98,73,5,226,210,108,228,13,98,135,122, 217,50,86,130,209,182,162,97,138,162,199,23,74,127,43,58,135,2,122,207,162,0,238,114,13,178,252,108,78,144,91,209,26,10, 112,39,79,124,170,138,156,112,190,243,205,125,61,126,90,250,217,211,210,162,79,165,228,156,119,197,104,5,83,54,231,51, 148,35,243,148,44,87,178,74,249,55,225,51,148,72,71,84,58,130,217,212,41,123,247,83,231,163,154,235,236,57,202,213,92, 103,207,79,71,247,200,239,98,184,164,57,199,46,100,161,76,235,170,110,183,202,115,195,143,43,155,71,201,124,37,125,234, 89,63,90,228,204,175,58,207,213,51,33,53,127,226,51,147,200,111,86,109,108,206,105,183,96,161,146,45,234,121,166,238,26, 66,22,77,219,138,84,93,206,115,129,233,186,152,250,28,131,182,182,199,173,120,102,57,149,173,182,71,147,182,101,90,153, 205,166,153,234,141,155,19,45,59,141,113,220,161,215,17,95,215,65,172,131,120,7,196,122,226,235,59,169,124,131,185,103, 192,54,82,131,107,226,233,209,120,58,221,25,79,103,76,203,76,17,235,36,222,9,215,206,78,210,58,241,86,214,105,88,131,41, 59,62,216,106,36,147,173,43,99,153,248,120,60,179,167,141,46,56,213,158,76,38,226,49,35,19,183,173,134,172,79,103,124, 200,140,237,137,37,204,213,70,34,49,96,196,118,165,219,168,226,92,79,229,102,197,108,11,109,201,180,174,22,114,50,147, 155,53,156,50,146,35,241,88,186,117,181,97,141,27,40,176,230,44,89,118,194,78,173,139,39,50,102,234,220,249,93,70,38,21, 159,108,163,121,239,153,127,74,81,179,207,116,221,108,196,45,180,175,252,204,156,45,102,12,25,37,211,25,118,186,117,213, 152,53,152,48,219,168,52,215,216,177,42,110,13,138,210,103,202,24,199,204,181,98,122,214,142,155,162,240,202,83,51,186, 108,49,92,42,111,222,169,121,98,206,27,54,89,235,236,216,88,122,245,136,97,13,155,217,105,205,109,202,180,107,110,151, 166,141,151,166,236,177,100,27,93,120,102,78,79,202,52,55,13,164,205,212,184,153,66,45,151,38,236,1,35,209,105,236,177, 199,50,51,213,204,121,239,231,218,168,229,84,135,184,149,28,203,140,154,153,17,123,176,117,149,145,54,59,68,26,19,111,97, 252,228,178,104,60,183,255,218,193,120,198,78,117,88,67,118,27,205,63,183,219,25,69,46,124,31,223,46,169,119,25,150,49, 44,90,188,174,51,102,143,182,166,236,68,188,117,231,88,204,108,61,99,155,53,156,99,47,53,156,218,243,165,127,105,57,109, 84,251,126,143,182,81,93,231,160,145,24,143,239,106,53,44,203,206,200,61,213,186,214,138,37,236,116,220,26,94,157,48,210, 114,179,156,233,211,129,113,73,169,252,218,179,228,119,153,163,3,202,193,76,139,21,35,98,74,107,2,139,171,21,75,44,213, 109,238,30,51,173,24,150,117,113,110,142,83,94,93,142,169,35,145,48,135,141,196,202,88,204,76,167,215,78,198,204,164,51, 25,13,103,241,73,13,143,141,162,115,57,94,37,185,94,136,10,195,206,168,204,24,55,218,221,99,177,17,103,230,114,158,11, 230,184,108,26,216,41,55,101,117,142,173,219,140,141,165,16,171,206,241,72,55,130,128,53,44,86,204,140,45,101,14,37,80, 14,154,49,110,59,177,171,199,72,13,155,185,173,173,60,139,187,211,180,54,210,123,182,109,94,75,190,220,165,65,172,151, 120,111,7,185,122,59,240,130,186,158,220,189,235,59,214,173,91,79,58,100,135,120,23,225,184,119,125,31,50,133,210,185,94, 188,73,173,15,185,157,125,8,234,189,125,120,170,79,150,192,250,72,235,19,207,225,173,83,168,136,233,125,66,17,129,189,31, 199,65,127,7,5,251,207,156,175,146,254,179,12,151,215,144,83,214,16,141,70,167,245,69,57,250,121,57,250,249,57,250,5,208, 11,28,125,93,194,24,78,147,219,144,251,79,24,133,236,52,6,204,4,229,25,234,180,160,10,99,112,240,236,81,133,216,0,21,139, 3,100,213,88,38,99,91,155,83,40,210,28,36,247,128,141,228,40,164,12,172,228,142,201,51,129,60,49,25,250,6,201,133,179, 199,72,81,65,204,30,52,55,219,136,212,43,51,34,49,29,221,201,47,19,61,41,195,74,15,217,169,81,42,20,39,15,66,122,90,122, 163,32,231,0,66,65,246,24,210,250,96,124,104,136,152,73,46,83,132,95,242,13,205,4,218,65,202,199,26,88,233,244,112,150, 80,103,206,54,117,142,81,33,204,98,207,160,203,102,42,77,121,34,41,6,158,188,66,83,78,62,177,148,68,241,61,241,81,83,22, 122,153,25,31,30,201,80,9,212,78,181,226,54,89,221,49,44,32,75,230,59,43,139,138,160,202,118,99,183,202,230,250,102,12, 29,131,228,65,106,139,49,113,101,86,217,70,5,66,177,237,140,136,31,20,64,162,123,15,198,123,180,27,107,50,30,51,201,15, 203,86,43,46,6,79,52,90,214,127,122,56,151,93,234,141,167,227,3,241,132,152,67,241,204,21,56,208,236,137,30,123,23,154, 23,154,78,75,167,132,137,200,150,76,24,123,214,165,12,116,78,71,238,149,242,29,87,219,17,42,194,64,98,30,49,112,155,141, 49,49,193,129,105,195,22,51,141,136,48,109,89,53,189,22,168,208,177,32,114,174,177,39,176,182,166,147,91,147,84,58,157, 144,81,245,178,248,224,32,218,164,170,233,178,81,135,124,230,20,67,202,24,206,150,41,13,40,70,149,41,207,122,202,27,49, 210,242,124,165,242,145,248,160,217,109,15,101,228,153,177,46,101,143,58,61,133,11,28,123,196,92,234,35,118,58,67,44,78, 94,204,229,38,25,28,210,164,197,71,71,169,72,92,217,226,70,98,181,145,76,119,97,132,169,80,25,186,205,196,90,107,112,58, 31,201,238,140,145,202,80,190,60,165,122,246,36,77,242,73,245,26,231,196,34,119,28,113,104,151,137,42,210,29,86,58,99,32, 22,83,94,60,189,41,105,32,48,227,177,180,26,121,242,236,50,247,172,22,85,149,239,58,199,213,175,48,155,209,61,34,198,197, 149,144,59,180,16,243,101,166,68,205,27,113,228,144,158,48,135,50,228,78,152,214,112,102,132,220,170,21,204,34,221,18, 115,234,177,204,137,141,114,114,237,196,224,136,124,159,160,98,219,202,94,10,87,167,76,35,131,153,44,153,49,173,49,211, 153,148,189,71,76,239,140,81,45,129,156,39,179,107,160,106,198,212,109,140,155,217,78,99,152,50,102,174,191,28,183,83, 139,232,206,216,201,36,76,133,182,37,150,80,54,144,148,99,139,202,102,157,118,83,32,183,109,97,65,76,8,255,156,59,21,249, 237,83,194,20,229,219,86,118,253,21,74,181,107,44,145,137,39,197,152,203,36,214,80,158,136,119,210,25,30,221,241,15,152, 217,168,225,195,241,97,227,228,146,91,30,21,58,211,230,113,228,53,120,110,12,81,43,131,104,225,74,202,245,231,77,26,41, 120,202,61,235,74,202,48,197,82,84,151,50,135,197,44,166,206,125,247,166,80,202,28,181,199,77,167,229,155,172,211,66,172, 43,37,131,140,150,54,51,228,79,139,112,52,125,243,37,31,210,178,255,134,88,71,229,185,169,14,167,245,114,9,139,199,114, 238,79,242,177,206,236,218,161,217,72,157,245,106,74,179,210,217,208,179,53,158,19,75,170,206,106,22,55,31,3,97,60,237,4, 35,185,212,10,211,167,4,33,111,54,153,112,218,116,69,60,145,216,104,103,228,76,250,210,88,218,217,128,128,7,145,154,222, 194,112,22,75,198,105,23,142,125,100,99,189,204,36,103,167,157,214,116,204,212,165,122,170,103,70,226,56,223,196,123,67, 84,201,69,176,138,8,174,161,12,168,98,8,242,198,50,67,75,100,44,101,227,228,26,55,18,98,166,165,216,52,68,186,184,139,82, 145,120,207,93,31,249,194,208,99,111,77,155,20,24,63,61,250,122,199,103,122,205,38,136,77,18,159,140,130,69,196,246,208, 65,206,200,227,239,107,167,67,248,0,220,220,175,241,175,179,194,189,26,251,23,86,50,71,163,56,111,153,252,237,206,118,86, 92,28,111,231,233,234,118,122,144,115,122,149,121,252,252,226,109,252,210,137,133,244,113,206,94,71,242,12,249,8,10,243, 63,78,159,115,68,141,54,252,21,118,55,243,52,243,23,168,141,191,201,38,248,215,63,56,113,43,227,46,239,202,133,237,45, 237,237,203,251,53,26,244,94,167,49,179,165,253,145,90,77,251,52,91,192,202,103,69,107,52,254,16,227,172,184,220,197,249, 229,213,46,114,49,151,230,246,242,5,15,187,188,110,114,51,55,119,107,243,231,243,241,102,23,159,207,211,205,84,225,84,93, 193,95,103,255,37,148,151,68,199,110,11,17,206,50,255,6,122,66,227,191,100,199,133,125,39,210,244,168,38,222,143,105,188, 239,26,200,23,53,214,7,241,140,20,120,228,23,82,249,80,136,142,40,135,159,57,14,223,116,196,207,57,251,42,243,84,111,216, 176,176,111,67,95,11,25,108,135,124,234,70,141,191,196,238,64,21,31,170,90,72,191,100,252,19,108,151,167,122,47,15,86, 243,100,53,47,106,251,52,207,84,111,255,52,159,172,166,219,185,246,9,54,130,76,94,120,11,31,175,190,167,127,231,94,141, 126,202,120,31,221,200,229,83,254,189,225,208,61,244,123,238,50,62,197,126,194,158,99,87,163,210,19,92,127,141,221,196, 62,203,62,131,26,150,237,237,163,61,210,145,31,166,106,254,212,245,213,27,180,252,43,121,167,230,57,198,48,133,180,141, 175,104,102,37,69,81,135,64,167,86,240,8,227,203,218,53,223,215,88,235,50,198,52,239,71,24,95,200,66,133,151,184,188,46, 223,34,87,193,78,183,183,133,149,148,241,107,219,218,221,190,101,172,122,150,176,159,106,228,235,88,181,159,238,214,216, 47,80,127,88,99,71,49,73,193,50,238,107,230,163,213,88,42,59,35,53,46,18,178,169,222,69,47,71,231,211,135,53,182,95,12, 247,65,141,109,247,248,227,33,250,54,99,255,9,195,179,26,237,99,149,45,59,55,76,238,168,216,75,188,154,189,196,102,87, 241,26,222,171,243,71,88,249,69,142,33,36,13,65,24,242,249,28,24,66,108,118,101,86,169,34,206,152,151,179,187,194,181,83, 83,250,243,229,117,236,173,114,210,220,228,187,43,140,213,194,235,111,152,210,15,85,176,91,195,175,137,183,169,74,188, 221,87,201,248,1,112,180,146,244,162,138,34,206,228,223,60,56,78,85,33,251,193,26,188,29,170,209,111,228,148,15,216,159, 64,8,52,179,35,53,140,77,205,97,236,129,57,165,236,0,228,97,112,28,76,133,25,219,7,158,5,39,193,173,181,240,1,7,192,205, 117,140,29,2,199,5,245,140,29,109,96,250,190,70,166,239,111,100,236,88,163,206,30,158,15,191,5,156,61,11,94,91,160,190, 203,201,126,71,150,149,217,223,97,138,239,120,178,191,197,20,223,9,101,127,143,169,211,204,111,50,197,119,74,217,223,101, 102,191,183,18,191,205,212,2,142,46,190,171,99,97,231,55,72,207,67,119,135,29,187,248,63,54,11,56,223,171,201,255,109, 135,157,122,197,111,57,53,229,47,254,231,172,135,157,114,197,255,169,73,61,43,255,255,29,112,218,42,126,55,250,127,111, 26,247,20,112,42,0,0}; //============================================================================== #if JUCE_PUSH_NOTIFICATIONS && JUCE_MODULE_AVAILABLE_juce_gui_extra // Returns true if the intent was handled. extern bool juce_handleNotificationIntent (void*); extern void juce_firebaseDeviceNotificationsTokenRefreshed (void*); extern void juce_firebaseRemoteNotificationReceived (void*); extern void juce_firebaseRemoteMessagesDeleted(); extern void juce_firebaseRemoteMessageSent(void*); extern void juce_firebaseRemoteMessageSendError (void*, void*); #endif #if JUCE_IN_APP_PURCHASES && JUCE_MODULE_AVAILABLE_juce_product_unlocking extern void juce_inAppPurchaseCompleted (void*); #endif extern void juce_contentSharingCompleted (int); //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (create, "", "(II)V") DECLARE_JNI_CLASS (AndroidLayoutParams, "android/view/ViewGroup$LayoutParams") #undef JNI_CLASS_MEMBERS //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (addView, "addView", "(Landroid/view/View;Landroid/view/ViewGroup$LayoutParams;)V") \ METHOD (removeView, "removeView", "(Landroid/view/View;)V") \ METHOD (updateViewLayout, "updateViewLayout", "(Landroid/view/View;Landroid/view/ViewGroup$LayoutParams;)V") DECLARE_JNI_CLASS (AndroidViewManager, "android/view/ViewManager") #undef JNI_CLASS_MEMBERS //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (create, "", "(IIIIIII)V") \ FIELD (gravity, "gravity", "I") \ FIELD (windowAnimations, "windowAnimations", "I") DECLARE_JNI_CLASS (AndroidWindowManagerLayoutParams, "android/view/WindowManager$LayoutParams") #undef JNI_CLASS_MEMBERS //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (getDecorView, "getDecorView", "()Landroid/view/View;") \ METHOD (setFlags, "setFlags", "(II)V") DECLARE_JNI_CLASS (AndroidWindow, "android/view/Window") #undef JNI_CLASS_MEMBERS //============================================================================== class AndroidComponentPeer : public ComponentPeer, private Timer { public: AndroidComponentPeer (Component& comp, const int windowStyleFlags, void* nativeViewHandle) : ComponentPeer (comp, windowStyleFlags), fullScreen (false), navBarsHidden (false), sizeAllocated (0), scale ((float) Desktop::getInstance().getDisplays().getMainDisplay().scale) { auto* env = getEnv(); // NB: must not put this in the initialiser list, as it invokes a callback, // which will fail if the peer is only half-constructed. view = GlobalRef (LocalRef (env->NewObject (ComponentPeerView, ComponentPeerView.create, getAppContext().get(), (jboolean) component.isOpaque(), (jlong) this))); if (nativeViewHandle != nullptr) { viewGroupIsWindow = false; // we don't know if the user is holding on to a local ref to this, so // explicitly create a new one auto nativeView = LocalRef(env->NewLocalRef(static_cast (nativeViewHandle))); if (env->IsInstanceOf (nativeView.get(), AndroidActivity)) { viewGroup = GlobalRef (nativeView); env->CallVoidMethod (viewGroup.get(), AndroidActivity.setContentView, view.get()); } else if (env->IsInstanceOf (nativeView.get(), AndroidViewGroup)) { viewGroup = GlobalRef (nativeView); LocalRef layoutParams (env->NewObject (AndroidLayoutParams, AndroidLayoutParams.create, -2, -2)); env->CallVoidMethod (view.get(), AndroidView.setLayoutParams, layoutParams.get()); env->CallVoidMethod ((jobject) viewGroup.get(), AndroidViewGroup.addView, view.get()); } else { // the native handle you passed as a second argument to Component::addToDesktop must // either be an Activity or a ViewGroup jassertfalse; } } else { viewGroupIsWindow = true; LocalRef viewLayoutParams (env->NewObject (AndroidLayoutParams, AndroidLayoutParams.create, -2, -2)); env->CallVoidMethod (view.get(), AndroidView.setLayoutParams, viewLayoutParams.get()); Rectangle physicalBounds = comp.getBoundsInParent() * scale; view.callVoidMethod (AndroidView.layout, physicalBounds.getX(), physicalBounds.getY(), physicalBounds.getRight(), physicalBounds.getBottom()); LocalRef windowLayoutParams (env->NewObject (AndroidWindowManagerLayoutParams, AndroidWindowManagerLayoutParams.create, physicalBounds.getWidth(), physicalBounds.getHeight(), physicalBounds.getX(), physicalBounds.getY(), TYPE_APPLICATION, FLAG_NOT_TOUCH_MODAL | FLAG_LAYOUT_IN_SCREEN | FLAG_LAYOUT_NO_LIMITS, component.isOpaque() ? PIXEL_FORMAT_OPAQUE : PIXEL_FORMAT_TRANSPARENT)); env->SetIntField (windowLayoutParams.get(), AndroidWindowManagerLayoutParams.gravity, GRAVITY_LEFT | GRAVITY_TOP); env->SetIntField (windowLayoutParams.get(), AndroidWindowManagerLayoutParams.windowAnimations, 0x01030000 /* android.R.style.Animation */); LocalRef activity (getCurrentActivity()); if (activity == nullptr) activity = getMainActivity(); viewGroup = GlobalRef (LocalRef (env->CallObjectMethod (activity.get(), AndroidContext.getSystemService, javaString ("window").get()))); env->CallVoidMethod (viewGroup.get(), AndroidViewManager.addView, view.get(), windowLayoutParams.get()); } if (isFocused()) handleFocusGain(); } ~AndroidComponentPeer() { auto* env = getEnv(); env->CallVoidMethod (view, ComponentPeerView.clear); frontWindow = nullptr; if (MessageManager::getInstance()->isThisTheMessageThread()) { if (env->IsInstanceOf (viewGroup.get(), AndroidActivity)) env->CallVoidMethod (viewGroup.get(), AndroidActivity.setContentView, nullptr); else env->CallVoidMethod (viewGroup.get(), AndroidViewManager.removeView, view.get()); } else { struct ViewDeleter : public CallbackMessage { ViewDeleter (const GlobalRef& view_, const GlobalRef& viewGroup_) : view (view_), group (viewGroup_) {} void messageCallback() override { auto* callbackEnv = getEnv(); if (callbackEnv->IsInstanceOf (group.get(), AndroidActivity)) callbackEnv->CallVoidMethod (group.get(), AndroidActivity.setContentView, nullptr); else callbackEnv->CallVoidMethod (group.get(), AndroidViewManager.removeView, view.get()); } private: GlobalRef view, group; }; (new ViewDeleter (view, viewGroup))->post(); } } void* getNativeHandle() const override { return (void*) view.get(); } void setVisible (bool shouldBeVisible) override { if (MessageManager::getInstance()->isThisTheMessageThread()) { view.callVoidMethod (ComponentPeerView.setVisible, shouldBeVisible); } else { struct VisibilityChanger : public CallbackMessage { VisibilityChanger (const GlobalRef& view_, bool shouldBeVisible_) : view (view_), shouldBeVisible (shouldBeVisible_) {} void messageCallback() override { view.callVoidMethod (ComponentPeerView.setVisible, shouldBeVisible); } GlobalRef view; bool shouldBeVisible; }; (new VisibilityChanger (view, shouldBeVisible))->post(); } } void setTitle (const String& title) override { view.callVoidMethod (ComponentPeerView.setViewName, javaString (title).get()); } void setBounds (const Rectangle& userRect, bool isNowFullScreen) override { Rectangle r = (userRect.toFloat() * scale).toNearestInt(); if (MessageManager::getInstance()->isThisTheMessageThread()) { auto* env = getEnv(); fullScreen = isNowFullScreen; { view.callVoidMethod (AndroidView.layout, r.getX(), r.getY(), r.getRight(), r.getBottom()); if (viewGroup != nullptr && viewGroupIsWindow) { LocalRef windowLayoutParams (env->NewObject (AndroidWindowManagerLayoutParams, AndroidWindowManagerLayoutParams.create, r.getWidth(), r.getHeight(), r.getX(), r.getY(), TYPE_APPLICATION, FLAG_NOT_TOUCH_MODAL | FLAG_LAYOUT_IN_SCREEN | FLAG_LAYOUT_NO_LIMITS, component.isOpaque() ? PIXEL_FORMAT_OPAQUE : PIXEL_FORMAT_TRANSPARENT)); env->SetIntField (windowLayoutParams.get(), AndroidWindowManagerLayoutParams.gravity, 0x3 /* LEFT */ | 0x30 /* TOP */); env->CallVoidMethod (viewGroup.get(), AndroidViewManager.updateViewLayout, view.get(), windowLayoutParams.get()); } } } else { class ViewMover : public CallbackMessage { public: ViewMover (const GlobalRef& v, const Rectangle& boundsToUse) : view (v), bounds (boundsToUse) {} void messageCallback() override { view.callVoidMethod (AndroidView.layout, bounds.getX(), bounds.getY(), bounds.getRight(), bounds.getBottom()); } private: GlobalRef view; Rectangle bounds; }; (new ViewMover (view, r))->post(); } } Rectangle getBounds() const override { Rectangle r (view.callIntMethod (AndroidView.getLeft), view.callIntMethod (AndroidView.getTop), view.callIntMethod (AndroidView.getWidth), view.callIntMethod (AndroidView.getHeight)); return r / scale; } void handleScreenSizeChange() override { ComponentPeer::handleScreenSizeChange(); if (isFullScreen()) setFullScreen (true); } Point getScreenPosition() const { auto* env = getEnv(); LocalRef position (env->NewIntArray (2)); env->CallVoidMethod (view.get(), AndroidView.getLocationOnScreen, position.get()); jint* const screenPosition = env->GetIntArrayElements (position.get(), 0); Point pos (screenPosition[0], screenPosition[1]); env->ReleaseIntArrayElements (position.get(), screenPosition, 0); return pos; } Point localToGlobal (Point relativePosition) override { return relativePosition + (getScreenPosition().toFloat() / scale); } Point globalToLocal (Point screenPosition) override { return screenPosition - (getScreenPosition().toFloat() / scale); } void setMinimised (bool /*shouldBeMinimised*/) override { // n/a } bool isMinimised() const override { return false; } bool shouldNavBarsBeHidden (bool shouldBeFullScreen) const { if (shouldBeFullScreen) if (Component* kiosk = Desktop::getInstance().getKioskModeComponent()) if (kiosk->getPeer() == this) return true; return false; } void setNavBarsHidden (bool hidden) { enum { SYSTEM_UI_FLAG_VISIBLE = 0, SYSTEM_UI_FLAG_LOW_PROFILE = 1, SYSTEM_UI_FLAG_HIDE_NAVIGATION = 2, SYSTEM_UI_FLAG_FULLSCREEN = 4, SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION = 512, SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN = 1024, SYSTEM_UI_FLAG_IMMERSIVE = 2048, SYSTEM_UI_FLAG_IMMERSIVE_STICKY = 4096 }; view.callVoidMethod (ComponentPeerView.setSystemUiVisibilityCompat, hidden ? (jint) (SYSTEM_UI_FLAG_HIDE_NAVIGATION | SYSTEM_UI_FLAG_FULLSCREEN | SYSTEM_UI_FLAG_IMMERSIVE_STICKY) : (jint) (SYSTEM_UI_FLAG_VISIBLE)); navBarsHidden = hidden; } void setFullScreen (bool shouldBeFullScreen) override { // updating the nav bar visibility is a bit odd on Android - need to wait for if (shouldNavBarsBeHidden (shouldBeFullScreen)) { if (! navBarsHidden && ! isTimerRunning()) { startTimer (500); } } else { setNavBarsHidden (false); } Rectangle r (shouldBeFullScreen ? Desktop::getInstance().getDisplays().getMainDisplay().userArea : lastNonFullscreenBounds); if ((! shouldBeFullScreen) && r.isEmpty()) r = getBounds(); // (can't call the component's setBounds method because that'll reset our fullscreen flag) if (! r.isEmpty()) setBounds (r, shouldBeFullScreen); component.repaint(); } bool isFullScreen() const override { return fullScreen; } void timerCallback() override { setNavBarsHidden (shouldNavBarsBeHidden (fullScreen)); setFullScreen (fullScreen); stopTimer(); } void setIcon (const Image& /*newIcon*/) override { // n/a } bool contains (Point localPos, bool trueIfInAChildWindow) const override { return isPositiveAndBelow (localPos.x, component.getWidth()) && isPositiveAndBelow (localPos.y, component.getHeight()) && ((! trueIfInAChildWindow) || view.callBooleanMethod (ComponentPeerView.containsPoint, localPos.x * scale, localPos.y * scale)); } BorderSize getFrameSize() const override { // TODO return BorderSize(); } bool setAlwaysOnTop (bool /*alwaysOnTop*/) override { // TODO return false; } void toFront (bool makeActive) override { // Avoid calling bringToFront excessively: it's very slow if (frontWindow != this) { view.callVoidMethod (AndroidView.bringToFront); frontWindow = this; } if (makeActive) grabFocus(); handleBroughtToFront(); } void toBehind (ComponentPeer*) override { // TODO } //============================================================================== void handleMouseDownCallback (int index, Point sysPos, int64 time) { lastMousePos = sysPos / scale; Point pos = globalToLocal (lastMousePos); // this forces a mouse-enter/up event, in case for some reason we didn't get a mouse-up before. handleMouseEvent (MouseInputSource::InputSourceType::touch, pos, ModifierKeys::currentModifiers.withoutMouseButtons(), MouseInputSource::invalidPressure, MouseInputSource::invalidOrientation, time, {}, index); if (isValidPeer (this)) handleMouseDragCallback (index, sysPos, time); } void handleMouseDragCallback (int index, Point sysPos, int64 time) { lastMousePos = sysPos / scale; Point pos = globalToLocal (lastMousePos); jassert (index < 64); touchesDown = (touchesDown | (1 << (index & 63))); ModifierKeys::currentModifiers = ModifierKeys::currentModifiers.withoutMouseButtons().withFlags (ModifierKeys::leftButtonModifier); handleMouseEvent (MouseInputSource::InputSourceType::touch, pos, ModifierKeys::currentModifiers.withoutMouseButtons().withFlags (ModifierKeys::leftButtonModifier), MouseInputSource::invalidPressure, MouseInputSource::invalidOrientation, time, {}, index); } void handleMouseUpCallback (int index, Point sysPos, int64 time) { lastMousePos = sysPos / scale; Point pos = globalToLocal (lastMousePos); jassert (index < 64); touchesDown = (touchesDown & ~(1 << (index & 63))); if (touchesDown == 0) ModifierKeys::currentModifiers = ModifierKeys::currentModifiers.withoutMouseButtons(); handleMouseEvent (MouseInputSource::InputSourceType::touch, pos, ModifierKeys::currentModifiers.withoutMouseButtons(), MouseInputSource::invalidPressure, MouseInputSource::invalidOrientation, time, {}, index); } void handleKeyDownCallback (int k, int kc) { handleKeyPress (k, static_cast (kc)); } void handleKeyUpCallback (int /*k*/, int /*kc*/) { } void handleBackButtonCallback() { if (auto* app = JUCEApplicationBase::getInstance()) app->backButtonPressed(); if (Component* kiosk = Desktop::getInstance().getKioskModeComponent()) if (kiosk->getPeer() == this) setNavBarsHidden (navBarsHidden); } void handleKeyboardHiddenCallback() { Component::unfocusAllComponents(); } void handleAppPausedCallback() {} void handleAppResumedCallback() { if (Component* kiosk = Desktop::getInstance().getKioskModeComponent()) if (kiosk->getPeer() == this) setNavBarsHidden (navBarsHidden); } //============================================================================== bool isFocused() const override { if (view != nullptr) return view.callBooleanMethod (AndroidView.hasFocus); return false; } void grabFocus() override { if (view != nullptr) view.callBooleanMethod (AndroidView.requestFocus); } void handleFocusChangeCallback (bool hasFocus) { if (hasFocus) handleFocusGain(); else handleFocusLoss(); } static const char* getVirtualKeyboardType (TextInputTarget::VirtualKeyboardType type) noexcept { switch (type) { case TextInputTarget::textKeyboard: return "text"; case TextInputTarget::numericKeyboard: return "number"; case TextInputTarget::decimalKeyboard: return "numberDecimal"; case TextInputTarget::urlKeyboard: return "textUri"; case TextInputTarget::emailAddressKeyboard: return "textEmailAddress"; case TextInputTarget::phoneNumberKeyboard: return "phone"; default: jassertfalse; break; } return "text"; } void textInputRequired (Point, TextInputTarget& target) override { view.callVoidMethod (ComponentPeerView.showKeyboard, javaString (getVirtualKeyboardType (target.getKeyboardType())).get()); } void dismissPendingTextInput() override { view.callVoidMethod (ComponentPeerView.showKeyboard, javaString ("").get()); // updating the nav bar visibility is a bit odd on Android - need to wait for if (! isTimerRunning()) hideNavBarDelayed(); } void hideNavBarDelayed() { startTimer (500); } //============================================================================== void handlePaintCallback (jobject canvas, jobject paint) { auto* env = getEnv(); jobject rect = env->CallObjectMethod (canvas, AndroidCanvas.getClipBounds); const int left = env->GetIntField (rect, AndroidRect.left); const int top = env->GetIntField (rect, AndroidRect.top); const int right = env->GetIntField (rect, AndroidRect.right); const int bottom = env->GetIntField (rect, AndroidRect.bottom); env->DeleteLocalRef (rect); const Rectangle clip (left, top, right - left, bottom - top); const int sizeNeeded = clip.getWidth() * clip.getHeight(); if (sizeAllocated < sizeNeeded) { buffer.clear(); sizeAllocated = sizeNeeded; buffer = GlobalRef (LocalRef ((jobject) env->NewIntArray (sizeNeeded))); } else if (sizeNeeded == 0) { return; } if (jint* dest = env->GetIntArrayElements ((jintArray) buffer.get(), 0)) { { Image temp (new PreallocatedImage (clip.getWidth(), clip.getHeight(), dest, ! component.isOpaque())); { LowLevelGraphicsSoftwareRenderer g (temp); g.setOrigin (-clip.getPosition()); g.addTransform (AffineTransform::scale (scale)); handlePaint (g); } } env->ReleaseIntArrayElements ((jintArray) buffer.get(), dest, 0); env->CallVoidMethod (canvas, AndroidCanvas.drawBitmap, (jintArray) buffer.get(), 0, clip.getWidth(), (jfloat) clip.getX(), (jfloat) clip.getY(), clip.getWidth(), clip.getHeight(), true, paint); } } void repaint (const Rectangle& userArea) override { Rectangle area = userArea * scale; if (MessageManager::getInstance()->isThisTheMessageThread()) { view.callVoidMethod (AndroidView.invalidate, area.getX(), area.getY(), area.getRight(), area.getBottom()); } else { struct ViewRepainter : public CallbackMessage { ViewRepainter (const GlobalRef& view_, const Rectangle& area_) : view (view_), area (area_) {} void messageCallback() override { view.callVoidMethod (AndroidView.invalidate, area.getX(), area.getY(), area.getRight(), area.getBottom()); } private: GlobalRef view; const Rectangle area; }; (new ViewRepainter (view, area))->post(); } } void performAnyPendingRepaintsNow() override { // TODO } void setAlpha (float /*newAlpha*/) override { // TODO } StringArray getAvailableRenderingEngines() override { return StringArray ("Software Renderer"); } //============================================================================== static Point lastMousePos; static int64 touchesDown; //============================================================================== struct StartupActivityCallbackListener : ActivityLifecycleCallbacks { void onActivityStarted (jobject /*activity*/) override { auto* env = getEnv(); LocalRef appContext (getAppContext()); if (appContext.get() != nullptr) { env->CallVoidMethod (appContext.get(), AndroidApplication.unregisterActivityLifecycleCallbacks, activityCallbackListener.get()); clear(); activityCallbackListener.clear(); const_cast (Desktop::getInstance().getDisplays()).refresh(); } } }; private: //============================================================================== GlobalRef view, viewGroup; bool viewGroupIsWindow = false; GlobalRef buffer; bool fullScreen; bool navBarsHidden; int sizeAllocated; float scale; //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (create, "", "(Landroid/content/Context;ZJ)V") \ METHOD (clear, "clear", "()V") \ METHOD (setViewName, "setViewName", "(Ljava/lang/String;)V") \ METHOD (setVisible, "setVisible", "(Z)V") \ METHOD (isVisible, "isVisible", "()Z") \ METHOD (containsPoint, "containsPoint", "(II)Z") \ METHOD (showKeyboard, "showKeyboard", "(Ljava/lang/String;)V") \ METHOD (setSystemUiVisibilityCompat, "setSystemUiVisibilityCompat", "(I)V") \ CALLBACK (handlePaintJni, "handlePaint", "(JLandroid/graphics/Canvas;Landroid/graphics/Paint;)V") \ CALLBACK (handleMouseDownJni, "handleMouseDown", "(JIFFJ)V") \ CALLBACK (handleMouseDragJni, "handleMouseDrag", "(JIFFJ)V") \ CALLBACK (handleMouseUpJni, "handleMouseUp", "(JIFFJ)V") \ CALLBACK (handleKeyDownJni, "handleKeyDown", "(JII)V") \ CALLBACK (handleKeyUpJni, "handleKeyUp", "(JII)V") \ CALLBACK (handleBackButtonJni, "handleBackButton", "(J)V") \ CALLBACK (handleKeyboardHiddenJni, "handleKeyboardHidden", "(J)V") \ CALLBACK (viewSizeChangedJni, "viewSizeChanged", "(J)V") \ CALLBACK (focusChangedJni, "focusChanged", "(JZ)V") \ CALLBACK (handleAppPausedJni, "handleAppPaused", "(J)V") \ CALLBACK (handleAppResumedJni, "handleAppResumed", "(J)V") \ DECLARE_JNI_CLASS_WITH_BYTECODE (ComponentPeerView, "com/roli/juce/ComponentPeerView", 16, javaComponentPeerView, sizeof(javaComponentPeerView)) #undef JNI_CLASS_MEMBERS static void JNICALL handlePaintJni (JNIEnv*, jobject /*view*/, jlong host, jobject canvas, jobject paint) { if (auto* myself = reinterpret_cast (host)) myself->handlePaintCallback (canvas, paint); } static void JNICALL handleMouseDownJni (JNIEnv*, jobject /*view*/, jlong host, jint i, jfloat x, jfloat y, jlong time) { if (auto* myself = reinterpret_cast (host)) myself->handleMouseDownCallback (i, Point ((float) x, (float) y), (int64) time); } static void JNICALL handleMouseDragJni (JNIEnv*, jobject /*view*/, jlong host, jint i, jfloat x, jfloat y, jlong time) { if (auto* myself = reinterpret_cast (host)) myself->handleMouseDragCallback (i, Point ((float) x, (float) y), (int64) time); } static void JNICALL handleMouseUpJni (JNIEnv*, jobject /*view*/, jlong host, jint i, jfloat x, jfloat y, jlong time) { if (auto* myself = reinterpret_cast (host)) myself->handleMouseUpCallback (i, Point ((float) x, (float) y), (int64) time); } static void JNICALL viewSizeChangedJni (JNIEnv*, jobject /*view*/, jlong host) { if (auto* myself = reinterpret_cast (host)) myself->handleMovedOrResized(); } static void JNICALL focusChangedJni (JNIEnv*, jobject /*view*/, jlong host, jboolean hasFocus) { if (auto* myself = reinterpret_cast (host)) myself->handleFocusChangeCallback (hasFocus); } static void JNICALL handleKeyDownJni (JNIEnv*, jobject /*view*/, jlong host, jint k, jint kc) { if (auto* myself = reinterpret_cast (host)) myself->handleKeyDownCallback ((int) k, (int) kc); } static void JNICALL handleKeyUpJni (JNIEnv*, jobject /*view*/, jlong host, jint k, jint kc) { if (auto* myself = reinterpret_cast (host)) myself->handleKeyUpCallback ((int) k, (int) kc); } static void JNICALL handleBackButtonJni (JNIEnv*, jobject /*view*/, jlong host) { if (auto* myself = reinterpret_cast (host)) myself->handleBackButtonCallback(); } static void JNICALL handleKeyboardHiddenJni (JNIEnv*, jobject /*view*/, jlong host) { if (auto* myself = reinterpret_cast (host)) myself->handleKeyboardHiddenCallback(); } static void JNICALL handleAppPausedJni (JNIEnv*, jobject /*view*/, jlong host) { if (auto* myself = reinterpret_cast (host)) myself->handleAppPausedCallback(); } static void JNICALL handleAppResumedJni (JNIEnv*, jobject /*view*/, jlong host) { if (auto* myself = reinterpret_cast (host)) myself->handleAppResumedCallback(); } //============================================================================== friend class Displays; static AndroidComponentPeer* frontWindow; static GlobalRef activityCallbackListener; //============================================================================== static constexpr int GRAVITY_LEFT = 0x3, GRAVITY_TOP = 0x30; static constexpr int TYPE_APPLICATION = 0x2; static constexpr int FLAG_NOT_TOUCH_MODAL = 0x20, FLAG_LAYOUT_IN_SCREEN = 0x100, FLAG_LAYOUT_NO_LIMITS = 0x200; static constexpr int PIXEL_FORMAT_OPAQUE = -1, PIXEL_FORMAT_TRANSPARENT = -2; struct PreallocatedImage : public ImagePixelData { PreallocatedImage (const int width_, const int height_, jint* data_, bool hasAlpha_) : ImagePixelData (Image::ARGB, width_, height_), data (data_), hasAlpha (hasAlpha_) { if (hasAlpha_) zeromem (data_, static_cast (width * height) * sizeof (jint)); } ~PreallocatedImage() { if (hasAlpha) { PixelARGB* pix = (PixelARGB*) data; for (int i = width * height; --i >= 0;) { pix->unpremultiply(); ++pix; } } } ImageType* createType() const override { return new SoftwareImageType(); } LowLevelGraphicsContext* createLowLevelContext() override { return new LowLevelGraphicsSoftwareRenderer (Image (this)); } void initialiseBitmapData (Image::BitmapData& bm, int x, int y, Image::BitmapData::ReadWriteMode /*mode*/) override { bm.lineStride = width * static_cast (sizeof (jint)); bm.pixelStride = static_cast (sizeof (jint)); bm.pixelFormat = Image::ARGB; bm.data = (uint8*) (data + x + y * width); } ImagePixelData::Ptr clone() override { PreallocatedImage* s = new PreallocatedImage (width, height, 0, hasAlpha); s->allocatedData.malloc (sizeof (jint) * static_cast (width * height)); s->data = s->allocatedData; memcpy (s->data, data, sizeof (jint) * static_cast (width * height)); return s; } private: jint* data; HeapBlock allocatedData; bool hasAlpha; JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (PreallocatedImage) }; JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (AndroidComponentPeer) }; Point AndroidComponentPeer::lastMousePos; int64 AndroidComponentPeer::touchesDown = 0; AndroidComponentPeer* AndroidComponentPeer::frontWindow = nullptr; GlobalRef AndroidComponentPeer::activityCallbackListener; AndroidComponentPeer::ComponentPeerView_Class AndroidComponentPeer::ComponentPeerView; //============================================================================== ComponentPeer* Component::createNewPeer (int styleFlags, void* nativeWindow) { return new AndroidComponentPeer (*this, styleFlags, nativeWindow); } //============================================================================== bool Desktop::canUseSemiTransparentWindows() noexcept { return true; } double Desktop::getDefaultMasterScale() { return 1.0; } Desktop::DisplayOrientation Desktop::getCurrentOrientation() const { enum { ROTATION_0 = 0, ROTATION_90 = 1, ROTATION_180 = 2, ROTATION_270 = 3 }; JNIEnv* env = getEnv(); LocalRef windowServiceString (javaString ("window")); LocalRef windowManager = LocalRef (env->CallObjectMethod (getAppContext().get(), AndroidContext.getSystemService, windowServiceString.get())); if (windowManager.get() != 0) { LocalRef display = LocalRef (env->CallObjectMethod (windowManager, AndroidWindowManager.getDefaultDisplay)); if (display.get() != 0) { int rotation = env->CallIntMethod (display, AndroidDisplay.getRotation); switch (rotation) { case ROTATION_0: return upright; case ROTATION_90: return rotatedAntiClockwise; case ROTATION_180: return upsideDown; case ROTATION_270: return rotatedClockwise; } } } jassertfalse; return upright; } bool MouseInputSource::SourceList::addSource() { addSource (sources.size(), MouseInputSource::InputSourceType::touch); return true; } bool MouseInputSource::SourceList::canUseTouch() { return true; } Point MouseInputSource::getCurrentRawMousePosition() { return AndroidComponentPeer::lastMousePos; } void MouseInputSource::setRawMousePosition (Point) { // not needed } //============================================================================== bool KeyPress::isKeyCurrentlyDown (const int /*keyCode*/) { // TODO return false; } JUCE_API void JUCE_CALLTYPE Process::hide() { auto* env = getEnv(); LocalRef currentActivity (getCurrentActivity().get()); if (env->CallBooleanMethod (currentActivity.get(), AndroidActivity.moveTaskToBack, true) == 0) { GlobalRef intent (LocalRef (env->NewObject (AndroidIntent, AndroidIntent.constructor))); env->CallObjectMethod (intent, AndroidIntent.setAction, javaString ("android.intent.action.MAIN") .get()); env->CallObjectMethod (intent, AndroidIntent.addCategory, javaString ("android.intent.category.HOME").get()); env->CallVoidMethod (currentActivity.get(), AndroidContext.startActivity, intent.get()); } } //============================================================================== // TODO JUCE_API bool JUCE_CALLTYPE Process::isForegroundProcess() { return true; } JUCE_API void JUCE_CALLTYPE Process::makeForegroundProcess() {} //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (show, "show", "()V") DECLARE_JNI_CLASS (AndroidDialog, "android/app/Dialog") #undef JNI_CLASS_MEMBERS #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (construct, "", "(Landroid/content/Context;)V") \ METHOD (create, "create", "()Landroid/app/AlertDialog;") \ METHOD (setTitle, "setTitle", "(Ljava/lang/CharSequence;)Landroid/app/AlertDialog$Builder;") \ METHOD (setMessage, "setMessage", "(Ljava/lang/CharSequence;)Landroid/app/AlertDialog$Builder;") \ METHOD (setCancelable, "setCancelable", "(Z)Landroid/app/AlertDialog$Builder;") \ METHOD (setOnCancelListener, "setOnCancelListener", "(Landroid/content/DialogInterface$OnCancelListener;)Landroid/app/AlertDialog$Builder;") \ METHOD (setPositiveButton, "setPositiveButton", "(Ljava/lang/CharSequence;Landroid/content/DialogInterface$OnClickListener;)Landroid/app/AlertDialog$Builder;") \ METHOD (setNegativeButton, "setNegativeButton", "(Ljava/lang/CharSequence;Landroid/content/DialogInterface$OnClickListener;)Landroid/app/AlertDialog$Builder;") \ METHOD (setNeutralButton, "setNeutralButton", "(Ljava/lang/CharSequence;Landroid/content/DialogInterface$OnClickListener;)Landroid/app/AlertDialog$Builder;") DECLARE_JNI_CLASS (AndroidAlertDialogBuilder, "android/app/AlertDialog$Builder") #undef JNI_CLASS_MEMBERS #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (dismiss, "dismiss", "()V") DECLARE_JNI_CLASS (AndroidDialogInterface, "android/content/DialogInterface") #undef JNI_CLASS_MEMBERS #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ DECLARE_JNI_CLASS (AndroidDialogOnClickListener, "android/content/DialogInterface$OnClickListener") #undef JNI_CLASS_MEMBERS //============================================================================== class DialogListener : public juce::AndroidInterfaceImplementer { public: DialogListener (ModalComponentManager::Callback* callbackToUse, int resultToUse) : callback (callbackToUse), result (resultToUse) {} void onResult (jobject dialog) { auto* env = getEnv(); env->CallVoidMethod (dialog, AndroidDialogInterface.dismiss); if (callback != nullptr) callback->modalStateFinished (result); callback = nullptr; } private: jobject invoke (jobject proxy, jobject method, jobjectArray args) override { auto* env = getEnv(); auto methodName = juce::juceString ((jstring) env->CallObjectMethod (method, JavaMethod.getName)); if (methodName == "onCancel" || methodName == "onClick") { onResult (env->GetObjectArrayElement (args, 0)); return nullptr; } // invoke base class return AndroidInterfaceImplementer::invoke (proxy, method, args); } std::unique_ptr callback; int result; }; //============================================================================== static void createAndroidDialog (const String& title, const String& message, ModalComponentManager::Callback* callback, const String& positiveButton = {}, const String& negativeButton = {}, const String& neutralButton = {}) { auto* env = getEnv(); LocalRef builder (env->NewObject (AndroidAlertDialogBuilder, AndroidAlertDialogBuilder.construct, getMainActivity().get())); builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setTitle, javaString (title).get())); builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setMessage, javaString (message).get())); builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setCancelable, true)); builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setOnCancelListener, CreateJavaInterface (new DialogListener (callback, 0), "android/content/DialogInterface$OnCancelListener").get())); auto positiveButtonText = positiveButton.isEmpty() ? String ("OK") : positiveButton; builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setPositiveButton, javaString (positiveButtonText).get(), CreateJavaInterface (new DialogListener (callback, positiveButton.isEmpty() ? 0 : 1), "android/content/DialogInterface$OnClickListener").get())); if (negativeButton.isNotEmpty()) builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setNegativeButton, javaString (negativeButton).get(), CreateJavaInterface (new DialogListener (callback, neutralButton.isEmpty() ? 0 : 2), "android/content/DialogInterface$OnClickListener").get())); if (neutralButton.isNotEmpty()) builder = LocalRef (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.setNegativeButton, javaString (neutralButton).get(), CreateJavaInterface (new DialogListener (callback, 0), "android/content/DialogInterface$OnClickListener").get())); LocalRef dialog (env->CallObjectMethod (builder.get(), AndroidAlertDialogBuilder.create)); env->CallVoidMethod (dialog.get(), AndroidDialog.show); } void JUCE_CALLTYPE NativeMessageBox::showMessageBoxAsync (AlertWindow::AlertIconType /*iconType*/, const String& title, const String& message, Component* /*associatedComponent*/, ModalComponentManager::Callback* callback) { createAndroidDialog (title, message, callback); } bool JUCE_CALLTYPE NativeMessageBox::showOkCancelBox (AlertWindow::AlertIconType /*iconType*/, const String& title, const String& message, Component* /*associatedComponent*/, ModalComponentManager::Callback* callback) { jassert (callback != nullptr); // on android, all alerts must be non-modal!! createAndroidDialog (title, message, callback, "OK", "Cancel"); return false; } int JUCE_CALLTYPE NativeMessageBox::showYesNoCancelBox (AlertWindow::AlertIconType /*iconType*/, const String& title, const String& message, Component* /*associatedComponent*/, ModalComponentManager::Callback* callback) { jassert (callback != nullptr); // on android, all alerts must be non-modal!! createAndroidDialog (title, message, callback, "Yes", "No", "Cancel"); return 0; } int JUCE_CALLTYPE NativeMessageBox::showYesNoBox (AlertWindow::AlertIconType /*iconType*/, const String& title, const String& message, Component* /*associatedComponent*/, ModalComponentManager::Callback* callback) { jassert (callback != nullptr); // on android, all alerts must be non-modal!! createAndroidDialog (title, message, callback, "Yes", "No"); return 0; } //============================================================================== static bool androidScreenSaverEnabled = false; void Desktop::setScreenSaverEnabled (const bool shouldEnable) { constexpr auto FLAG_KEEP_SCREEN_ON = 0x80; if (shouldEnable != androidScreenSaverEnabled) { LocalRef activity (getMainActivity()); if (activity != nullptr) { auto* env = getEnv(); LocalRef mainWindow (env->CallObjectMethod (activity.get(), AndroidActivity.getWindow)); env->CallVoidMethod(mainWindow.get(), AndroidWindow.setFlags, shouldEnable ? FLAG_KEEP_SCREEN_ON : 0, FLAG_KEEP_SCREEN_ON); } androidScreenSaverEnabled = shouldEnable; } } bool Desktop::isScreenSaverEnabled() { return androidScreenSaverEnabled; } //============================================================================== void Desktop::setKioskComponent (Component* kioskComp, bool enableOrDisable, bool allowMenusAndBars) { ignoreUnused (allowMenusAndBars); if (AndroidComponentPeer* peer = dynamic_cast (kioskComp->getPeer())) peer->setFullScreen (enableOrDisable); else jassertfalse; // (this should have been checked by the caller) } //============================================================================== static jint getAndroidOrientationFlag (int orientations) noexcept { enum { SCREEN_ORIENTATION_LANDSCAPE = 0, SCREEN_ORIENTATION_PORTRAIT = 1, SCREEN_ORIENTATION_USER = 2, SCREEN_ORIENTATION_REVERSE_LANDSCAPE = 8, SCREEN_ORIENTATION_REVERSE_PORTRAIT = 9, SCREEN_ORIENTATION_USER_LANDSCAPE = 11, SCREEN_ORIENTATION_USER_PORTRAIT = 12, }; switch (orientations) { case Desktop::upright: return (jint) SCREEN_ORIENTATION_PORTRAIT; case Desktop::upsideDown: return (jint) SCREEN_ORIENTATION_REVERSE_PORTRAIT; case Desktop::upright + Desktop::upsideDown: return (jint) SCREEN_ORIENTATION_USER_PORTRAIT; case Desktop::rotatedAntiClockwise: return (jint) SCREEN_ORIENTATION_LANDSCAPE; case Desktop::rotatedClockwise: return (jint) SCREEN_ORIENTATION_REVERSE_LANDSCAPE; case Desktop::rotatedClockwise + Desktop::rotatedAntiClockwise: return (jint) SCREEN_ORIENTATION_USER_LANDSCAPE; default: return (jint) SCREEN_ORIENTATION_USER; } } void Desktop::allowedOrientationsChanged() { LocalRef activity (getMainActivity()); if (activity != nullptr) getEnv()->CallVoidMethod (activity.get(), AndroidActivity.setRequestedOrientation, getAndroidOrientationFlag (allowedOrientations)); } //============================================================================== bool juce_areThereAnyAlwaysOnTopWindows() { return false; } //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (create, "", "()V") \ FIELD (density, "density", "F") \ FIELD (widthPixels, "widthPixels", "I") \ FIELD (heightPixels, "heightPixels", "I") DECLARE_JNI_CLASS (AndroidDisplayMetrics, "android/util/DisplayMetrics") #undef JNI_CLASS_MEMBERS //============================================================================== class LayoutChangeListener : public juce::AndroidInterfaceImplementer { public: virtual void onLayoutChange (LocalRef view, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) = 0; private: jobject invoke (jobject proxy, jobject method, jobjectArray args) override { auto* env = getEnv(); auto methodName = juce::juceString ((jstring) env->CallObjectMethod (method, JavaMethod.getName)); if (methodName == "onLayoutChange") { jassert (env->GetArrayLength (args) == 9); LocalRef view (env->GetObjectArrayElement (args, 0)); int dims[8]; for (int i = 1; i < 9; ++i) { LocalRef integer (env->GetObjectArrayElement (args, i)); dims[i - 1] = env->CallIntMethod (integer.get(), JavaInteger.intValue); } onLayoutChange (std::move (view), dims[0], dims[1], dims[2], dims[3], dims[4], dims[5], dims[6], dims[7]); return nullptr; } // invoke base class return AndroidInterfaceImplementer::invoke (proxy, method, args); } std::unique_ptr callback; }; //============================================================================== class MainActivityWindowLayoutListener : public LayoutChangeListener { public: void onLayoutChange (LocalRef /*view*/, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) override { auto newBounds = Rectangle::leftTopRightBottom (left, top, right, bottom); auto oldBounds = Rectangle::leftTopRightBottom (oldLeft, oldTop, oldRight, oldBottom); if (newBounds != oldBounds) { auto& displays = Desktop::getInstance().getDisplays(); auto& mainDisplay = displays.getMainDisplay(); Rectangle userArea = newBounds / mainDisplay.scale; if (userArea != mainDisplay.userArea) const_cast (displays).refresh(); } } }; //============================================================================== void Displays::findDisplays (float masterScale) { auto* env = getEnv(); LocalRef usableSize (env->NewObject (AndroidPoint, AndroidPoint.create, 0, 0)); LocalRef windowServiceString (javaString ("window")); LocalRef displayMetrics (env->NewObject (AndroidDisplayMetrics, AndroidDisplayMetrics.create)); LocalRef windowManager (env->CallObjectMethod (getAppContext().get(), AndroidContext.getSystemService, windowServiceString.get())); LocalRef display (env->CallObjectMethod (windowManager, AndroidWindowManager.getDefaultDisplay)); jmethodID getRealMetricsMethod = env->GetMethodID (AndroidDisplay, "getRealMetrics", "(Landroid/util/DisplayMetrics;)V"); if (getRealMetricsMethod != 0) env->CallVoidMethod (display.get(), getRealMetricsMethod, displayMetrics.get()); else env->CallVoidMethod (display.get(), AndroidDisplay.getMetrics, displayMetrics.get()); env->CallVoidMethod (display.get(), AndroidDisplay.getSize, usableSize.get()); Display d; d.isMain = true; d.scale = env->GetFloatField (displayMetrics.get(), AndroidDisplayMetrics.density); d.dpi = (d.scale * 160.f); d.scale *= masterScale; d.totalArea = Rectangle (env->GetIntField (displayMetrics.get(), AndroidDisplayMetrics.widthPixels), env->GetIntField (displayMetrics.get(), AndroidDisplayMetrics.heightPixels)) / d.scale; d.userArea = Rectangle (env->GetIntField (usableSize.get(), AndroidPoint.x), env->GetIntField (usableSize.get(), AndroidPoint.y)) / d.scale; // unfortunately usableSize still contains the nav bar // the best workaround is to try to get the size of the top-level view of // the main activity LocalRef activity (getMainActivity()); if (activity != nullptr) { LocalRef mainWindow (env->CallObjectMethod (activity.get(), AndroidActivity.getWindow)); LocalRef decorView (env->CallObjectMethod (mainWindow.get(), AndroidWindow.getDecorView)); LocalRef contentView (env->CallObjectMethod (decorView.get(), AndroidView.findViewById, 0x01020002 /* android.R.id.content */)); if (contentView != nullptr) { Rectangle activityArea (env->CallIntMethod (contentView.get(), AndroidView.getLeft), env->CallIntMethod (contentView.get(), AndroidView.getTop), env->CallIntMethod (contentView.get(), AndroidView.getWidth), env->CallIntMethod (contentView.get(), AndroidView.getHeight)); if (! activityArea.isEmpty()) d.userArea = activityArea / d.scale; static bool hasAddedMainActivityListener = false; if (! hasAddedMainActivityListener) { hasAddedMainActivityListener = true; env->CallVoidMethod (contentView.get(), AndroidView.addOnLayoutChangeListener, CreateJavaInterface (new MainActivityWindowLayoutListener, "android/view/View$OnLayoutChangeListener").get()); } } } else { // the main activity may have not started yet so add an activity listener if (AndroidComponentPeer::activityCallbackListener == nullptr) { LocalRef appContext (getAppContext()); if (appContext.get() != nullptr) { AndroidComponentPeer::activityCallbackListener = GlobalRef (CreateJavaInterface ( new AndroidComponentPeer::StartupActivityCallbackListener, "android/app/Application$ActivityLifecycleCallbacks")); env->CallVoidMethod (appContext.get(), AndroidApplication.registerActivityLifecycleCallbacks, AndroidComponentPeer::activityCallbackListener.get()); } } } displays.add (d); } //============================================================================== Image juce_createIconForFile (const File& /*file*/) { return Image(); } //============================================================================== void* CustomMouseCursorInfo::create() const { return nullptr; } void* MouseCursor::createStandardMouseCursor (const MouseCursor::StandardCursorType) { return nullptr; } void MouseCursor::deleteMouseCursor (void* const /*cursorHandle*/, const bool /*isStandard*/) {} //============================================================================== void MouseCursor::showInWindow (ComponentPeer*) const {} //============================================================================== bool DragAndDropContainer::performExternalDragDropOfFiles (const StringArray& /*files*/, const bool /*canMove*/, Component* /*srcComp*/, std::function /*callback*/) { jassertfalse; // no such thing on Android! return false; } bool DragAndDropContainer::performExternalDragDropOfText (const String& /*text*/, Component* /*srcComp*/, std::function /*callback*/) { jassertfalse; // no such thing on Android! return false; } //============================================================================== void LookAndFeel::playAlertSound() { } //============================================================================== #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \ METHOD (getText, "getText", "()Ljava/lang/CharSequence;") \ METHOD (setText, "setText", "(Ljava/lang/CharSequence;)V") DECLARE_JNI_CLASS (AndroidClipboardManager, "android/content/ClipboardManager") #undef JNI_CLASS_MEMBERS //============================================================================== void SystemClipboard::copyTextToClipboard (const String& text) { auto* env = getEnv(); LocalRef clipboardManager (env->CallObjectMethod (getAppContext().get(), AndroidContext.getSystemService, javaString ("clipboard").get())); env->CallVoidMethod (clipboardManager.get(), AndroidClipboardManager.setText, javaString(text).get()); } String SystemClipboard::getTextFromClipboard() { auto* env = getEnv(); LocalRef clipboardManager (env->CallObjectMethod (getAppContext().get(), AndroidContext.getSystemService, javaString ("clipboard").get())); LocalRef charSequence (env->CallObjectMethod (clipboardManager.get(), AndroidClipboardManager.getText)); if (charSequence == nullptr) return {}; return juceString(LocalRef ((jstring) env->CallObjectMethod(charSequence.get(), JavaCharSequence.toString))); } //============================================================================== const int extendedKeyModifier = 0x10000; const int KeyPress::spaceKey = ' '; const int KeyPress::returnKey = 66; const int KeyPress::escapeKey = 4; const int KeyPress::backspaceKey = 67; const int KeyPress::leftKey = extendedKeyModifier + 1; const int KeyPress::rightKey = extendedKeyModifier + 2; const int KeyPress::upKey = extendedKeyModifier + 3; const int KeyPress::downKey = extendedKeyModifier + 4; const int KeyPress::pageUpKey = extendedKeyModifier + 5; const int KeyPress::pageDownKey = extendedKeyModifier + 6; const int KeyPress::endKey = extendedKeyModifier + 7; const int KeyPress::homeKey = extendedKeyModifier + 8; const int KeyPress::deleteKey = extendedKeyModifier + 9; const int KeyPress::insertKey = -1; const int KeyPress::tabKey = 61; const int KeyPress::F1Key = extendedKeyModifier + 10; const int KeyPress::F2Key = extendedKeyModifier + 11; const int KeyPress::F3Key = extendedKeyModifier + 12; const int KeyPress::F4Key = extendedKeyModifier + 13; const int KeyPress::F5Key = extendedKeyModifier + 14; const int KeyPress::F6Key = extendedKeyModifier + 16; const int KeyPress::F7Key = extendedKeyModifier + 17; const int KeyPress::F8Key = extendedKeyModifier + 18; const int KeyPress::F9Key = extendedKeyModifier + 19; const int KeyPress::F10Key = extendedKeyModifier + 20; const int KeyPress::F11Key = extendedKeyModifier + 21; const int KeyPress::F12Key = extendedKeyModifier + 22; const int KeyPress::F13Key = extendedKeyModifier + 23; const int KeyPress::F14Key = extendedKeyModifier + 24; const int KeyPress::F15Key = extendedKeyModifier + 25; const int KeyPress::F16Key = extendedKeyModifier + 26; const int KeyPress::F17Key = extendedKeyModifier + 50; const int KeyPress::F18Key = extendedKeyModifier + 51; const int KeyPress::F19Key = extendedKeyModifier + 52; const int KeyPress::F20Key = extendedKeyModifier + 53; const int KeyPress::F21Key = extendedKeyModifier + 54; const int KeyPress::F22Key = extendedKeyModifier + 55; const int KeyPress::F23Key = extendedKeyModifier + 56; const int KeyPress::F24Key = extendedKeyModifier + 57; const int KeyPress::F25Key = extendedKeyModifier + 58; const int KeyPress::F26Key = extendedKeyModifier + 59; const int KeyPress::F27Key = extendedKeyModifier + 60; const int KeyPress::F28Key = extendedKeyModifier + 61; const int KeyPress::F29Key = extendedKeyModifier + 62; const int KeyPress::F30Key = extendedKeyModifier + 63; const int KeyPress::F31Key = extendedKeyModifier + 64; const int KeyPress::F32Key = extendedKeyModifier + 65; const int KeyPress::F33Key = extendedKeyModifier + 66; const int KeyPress::F34Key = extendedKeyModifier + 67; const int KeyPress::F35Key = extendedKeyModifier + 68; const int KeyPress::numberPad0 = extendedKeyModifier + 27; const int KeyPress::numberPad1 = extendedKeyModifier + 28; const int KeyPress::numberPad2 = extendedKeyModifier + 29; const int KeyPress::numberPad3 = extendedKeyModifier + 30; const int KeyPress::numberPad4 = extendedKeyModifier + 31; const int KeyPress::numberPad5 = extendedKeyModifier + 32; const int KeyPress::numberPad6 = extendedKeyModifier + 33; const int KeyPress::numberPad7 = extendedKeyModifier + 34; const int KeyPress::numberPad8 = extendedKeyModifier + 35; const int KeyPress::numberPad9 = extendedKeyModifier + 36; const int KeyPress::numberPadAdd = extendedKeyModifier + 37; const int KeyPress::numberPadSubtract = extendedKeyModifier + 38; const int KeyPress::numberPadMultiply = extendedKeyModifier + 39; const int KeyPress::numberPadDivide = extendedKeyModifier + 40; const int KeyPress::numberPadSeparator = extendedKeyModifier + 41; const int KeyPress::numberPadDecimalPoint = extendedKeyModifier + 42; const int KeyPress::numberPadEquals = extendedKeyModifier + 43; const int KeyPress::numberPadDelete = extendedKeyModifier + 44; const int KeyPress::playKey = extendedKeyModifier + 45; const int KeyPress::stopKey = extendedKeyModifier + 46; const int KeyPress::fastForwardKey = extendedKeyModifier + 47; const int KeyPress::rewindKey = extendedKeyModifier + 48; } // namespace juce