Get characters above Baseline
So I want to be able to fill a Rectangle with a String on my JFrame. I basically have everything working but one small part. The problem is that some characters such as "g" or "," are going below the so called baseline at which others such as "e" are drawn. I want to only find the ones that are above the "line" in a String.
This is my current code (sorry for not complying to java conventions):
public static final void DrawString(String Message, ERect Bounds, Color Color, Font Font)
{
// Gets Font Render Context
FontRenderContext FRC = CanvasGraphics.getFontRenderContext();
// initializes the font size to some reasonable number
float FontSize = 25;
// Gets the bounds of the entire string
Rectangle StringBounds = Font.deriveFont(FontSize).createGlyphVector(FRC, Message).getPixelBounds(null, 0, 0);
// Approximates font size by looking at the ratio from expected dimensions to
// actual ones
FontSize *= EMath.Min(Bounds.GetWidth() / StringBounds.width, Bounds.GetHeight() / StringBounds.height);
// Ensures that that the font truly fills out the rect by checking if a bigger
// font would still fit
while (true)
{
// checks new height
StringBounds = Font.deriveFont(FontSize + 1).createGlyphVector(FRC, Message).getPixelBounds(null, 0, 0);
// if it exceeds the bounds, we can use the previous font size
if (StringBounds.height > Bounds.GetHeight() || StringBounds.width > Bounds.GetWidth())
{
StringBounds = Font.deriveFont(FontSize).createGlyphVector(FRC, Message).getPixelBounds(null, 0, 0);
break;
}
// font wasn't big enough yet..
FontSize++;
}
// We set the font
Font = Font.deriveFont(FontSize);
// We get the entire height of the String
float TextHeight = Font.createGlyphVector(FRC, Message).getPixelBounds(null, 0, 0).height;
// !!! Problem
// Since some characters go below the y coordinate, such a 'g', we
// want to figure out what the height to the line is
float LineTextHeight = Font.createGlyphVector(FRC, GetAboveLineCharacters(Message)).getPixelBounds(null, 0, 0).height;
// !!! Problem
// We set the font and color
CanvasGraphics.setFont(Font);
CanvasGraphics.setColor(Color);
// We draw the string in the center of the box
CanvasGraphics.drawString(Message, Bounds.GetX() + (Bounds.GetWidth() - StringBounds.width) / 2,
Bounds.GetY() + (Bounds.GetHeight() - TextHeight) / 2 + LineTextHeight);
}
Basically I need an implementation for "GetAboveLineCharacter" or at least some way to get the height above the line (Problem being that strings like "A" and "e" have different heights.
Thank you very much for your help!
1 answer
-
answered 2019-08-13 10:50
mdre
Even though it doesn't cover all cases, this is my current workaround for most fonts from what I tested. Its by far not a general solution but it works fine for an approximate:
private static final String GetAboveLineCharacters(String ToTest) { final char blank = Character.MIN_VALUE; String ToReturn = ToTest.replace('g', blank).replace('y', blank).replace('p', blank).replace('q', blank) .replace('j', 'i').replace('J', 'A').replace('a', blank); return (ToReturn == "" ? "e" : ToReturn); }
See also questions close to this topic
-
SWT/RCP bypass modal dialog
Is it possible to ignore an SWT dialog's modality when it is raised?
The issue is that I have an Eclipse RCP application which can be displayed on multiple (8+ screens) at any given time; there can be a single modal dialog raised somewhere on any of the screens (i.e. a user clicks on the Help->About Eclipse page, which displays a modal dialog) which blocks/freezes the rest of the screens until the user finds it and closes it. This is quite problematic as it can be hidden somewhere among a mess of other GUIs.
Ideally it should be possible to interact with the rest of the GUI dialogs even though there is a modal dialog open somewhere. Is this possible?
The cleanest solution is to set the dialog to be non modal (of course) either when setting its style or by invoking the setBlockOnOpen(false); method on the configureShell(...). Unfortunately this is not an option, as the application uses built in eclipse plugins, which are set to modal by default. Is there a way to set it non blocking after it has been opened?
You can also force the modal dialog into the viewport via shell.forceActive(), however this is an ugly solution as it also brings the root swt window into view. If there is a way to just bring forward the modal dialog without its parent, this would be an ok solution.
SWT.shell is quite limited, but maybe there is some other way to mitigate this issue?
-
CXF WS-Security SOAP request no Header
Basically I generated the java classes from WSDL using the CXF 3.2.6 version, also i do have the provided request example to their soap service. I'm using Spring Boot purely java config.
The issue is: When I'm calling generated class port type i tried logging the request and i do not see any Header. I supposed I may am misunderstanding something over here, please guide me in
My question is: where is the problem ?
The problem is that It behaves literally the same as i would just call the service without doing any other thing.
ServicePort servicePort = webservice.getPort(); Client client = ClientProxy.getClient(servicePort); Init.init(); Properties properties = new Properties(); properties.setProperty("org.apache.ws.security.crypto.provider", "org.apache.ws.security.components.crypto.Merlin"); properties.setProperty("org.apache.ws.security.crypto.merlin.keystore.type", "jks"); properties.setProperty("org.apache.ws.security.crypto.merlin.keystore.password", keystorePassword); properties.setProperty("org.apache.ws.security.crypto.merlin.keystore.alias", "alias"); properties.setProperty("org.apache.ws.security.crypto.merlin.file", new ClassPathResource(keyStore).getPath()); properties.setProperty("org.apache.ws.security.crypto.merlin.keystore.private.password", keystorePassword); Merlin crypto = null; try { crypto = (Merlin) CryptoFactory.getInstance(properties); } catch (WSSecurityException e) { e.printStackTrace(); } STSClient stsClient = new STSClient(((EndpointImpl) client.getEndpoint()).getBus()); Map<String, Object> stsClientProperties = new HashMap<>(); stsClientProperties.put("ws-security.signature.crypto", crypto); stsClientProperties.put("ws-security.encryption.crypto", crypto); stsClient.setProperties(stsClientProperties); BindingProvider bindingProvider = (BindingProvider) servicePort; bindingProvider.getRequestContext().put("ws-security.sts.client", stsClient); ServiceResponse response = servicePort.myCall(...);
Request example i got:
<?xml version='1.0' encoding='utf-8'?> <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"> <soap:Header> <wsse:Security xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" soap:mustUnderstand="1"> <ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#" Id="SIG-****"> <ds:SignedInfo> <ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"> <ec:InclusiveNamespaces xmlns:ec="http://www.w3.org/2001/10/xml-exc-c14n#" PrefixList="soap"/> </ds:CanonicalizationMethod> <ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"/> <ds:Reference URI="#id-****"> <ds:Transforms> <ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/> </ds:Transforms> <ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/> <ds:DigestValue>****</ds:DigestValue> </ds:Reference> </ds:SignedInfo> <ds:SignatureValue> ***** </ds:SignatureValue> <ds:KeyInfo Id="****"> <wsse:SecurityTokenReference wsu:Id="*****0"> <ds:X509Data> <ds:X509IssuerSerial> <ds:X509IssuerName>******* </ds:X509IssuerName> <ds:X509SerialNumber>20</ds:X509SerialNumber> </ds:X509IssuerSerial> </ds:X509Data> </wsse:SecurityTokenReference> </ds:KeyInfo> </ds:Signature> </wsse:Security> </soap:Header> <soap:Body xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="id-****"> some data </soap:Body> </soap:Envelope>
-
Exception in thread "AWT-EventQueue-0" java.lang.NullPointerException in java list
Hello I'm a new programmer at an high school level as a result I do not know much about programming and am getting quite a few errors which have been resolved while others I completely do not understand. I am to make a simple java list selection program where the user gets to pick between a variety of plants choices. The program itself compiles perfectly(it's not ready yet) but when I run it however it gives me some complications.I'm trying to put some plants from a text file into the list and after that i'll press a button to buy it. As i said, the code it is not ready yet but i got this error and i can't understand why. Here is my program:
import java.io.BufferedReader; import java.io.FileReader; import java.io.IOException; import java.util.logging.Level; import java.util.logging.Logger; public class Home extends javax.swing.JFrame { public Home() { initComponents(); } @SuppressWarnings("unchecked") // <editor-fold defaultstate="collapsed" desc="Generated Code"> private void initComponents() { jFereastraLogin = new javax.swing.JPanel(); jPlafar = new javax.swing.JLabel(); jScrollPane1 = new javax.swing.JScrollPane(); jListaPlante = new javax.swing.JList<>(); jButtonCumpara = new javax.swing.JButton(); setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); jFereastraLogin.setBackground(new java.awt.Color(204, 204, 255)); jFereastraLogin.setBorder(javax.swing.BorderFactory.createTitledBorder("Home")); jFereastraLogin.setLayout(new org.netbeans.lib.awtextra.AbsoluteLayout()); jPlafar.setFont(new java.awt.Font("Tahoma", 1, 36)); // NOI18N jPlafar.setHorizontalAlignment(javax.swing.SwingConstants.CENTER); jPlafar.setText("PLAFAR"); jFereastraLogin.add(jPlafar, new org.netbeans.lib.awtextra.AbsoluteConstraints(0, 10, 580, 30)); jListaPlante.setFont(new java.awt.Font("Tahoma", 0, 14)); // NOI18N jListaPlante.setModel(new javax.swing.AbstractListModel<String>(){ String[] listaplante; public void citeste(){ /*int c; int k=0; listaplante = new String[10]; String planta = ""; FileReader f = null; try { f = new FileReader("Plante.txt"); while ((c = f.read()) != -1) { planta = planta + (char)c; // formez numele plantei } listaplante[k] = planta; k++; planta = ""; f.close(); } catch (FileNotFoundException e) { System.out.println("Fisierul nu a fost gasit"); } catch (IOException e) { System.out.println("Eroare la citire"); }*/ BufferedReader objReader = null; try { String strCurrentLine; objReader = new BufferedReader(new FileReader("Plante.txt")); while ((strCurrentLine = objReader.readLine()) != null) { System.out.println(strCurrentLine); } } catch (IOException e) { e.printStackTrace(); } finally { try { if (objReader != null) objReader.close(); }catch (IOException ex) { ex.printStackTrace(); } } } public int getSize() { return listaplante.length; } public String getElementAt(int i) { return listaplante[i]; } }); jScrollPane1.setViewportView(jListaPlante); jFereastraLogin.add(jScrollPane1, new org.netbeans.lib.awtextra.AbsoluteConstraints(10, 90, 560, 50)); jButtonCumpara.setText("CUMPARA"); jButtonCumpara.addActionListener(new java.awt.event.ActionListener() { public void actionPerformed(java.awt.event.ActionEvent evt) { jButtonCumparaActionPerformed(evt); } }); jFereastraLogin.add(jButtonCumpara, new org.netbeans.lib.awtextra.AbsoluteConstraints(240, 160, -1, -1)); javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane()); getContentPane().setLayout(layout); layout.setHorizontalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addComponent(jFereastraLogin, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) ); layout.setVerticalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addComponent(jFereastraLogin, javax.swing.GroupLayout.DEFAULT_SIZE, 375, Short.MAX_VALUE) ); pack(); }// </editor-fold> private void jButtonCumparaActionPerformed(java.awt.event.ActionEvent evt) { } public static void main(String args[]) { try { for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) { if ("Nimbus".equals(info.getName())) { javax.swing.UIManager.setLookAndFeel(info.getClassName()); break; } } } catch (ClassNotFoundException ex) { java.util.logging.Logger.getLogger(Home.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } catch (InstantiationException ex) { java.util.logging.Logger.getLogger(Home.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } catch (IllegalAccessException ex) { java.util.logging.Logger.getLogger(Home.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } catch (javax.swing.UnsupportedLookAndFeelException ex) { java.util.logging.Logger.getLogger(Home.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } java.awt.EventQueue.invokeLater(new Runnable() { public void run() { new Home().setVisible(true); } }); } // Variables declaration - do not modify private javax.swing.JButton jButtonCumpara; private javax.swing.JPanel jFereastraLogin; public javax.swing.JList<String> jListaPlante; private javax.swing.JLabel jPlafar; private javax.swing.JScrollPane jScrollPane1; // End of variables declaration }
-
DirectX12 ImGUI not visible
Trying to incorporate an ImGUI interface into a DXR project. The ImGUI files are in and compiling fine. I've copied an ImGUI setup from some else's DXR project to create a window and draw it over my application. However, although the GUI is initialized, updated, and rendered, it does not appear on the screen. I'm at a loss trying to figure out what I'm missing. Any help would be greatly appreciated.
Most of the functionality takes place in this file. Feel free to browse the rest of the project, though. (Please ignore the duplicate installation of imgui present at the project root directory. The version we are using is inside the src) All methods InitImGUI, StartFrameImGUI, RenderImGUI, and ShutdownImGUI are called during execution, so I'm not sure what's missing. https://github.com/aleward/Pudgy-Pals-Build-2.0.0-Even-Pudgier/blob/master/dxrProject5/src/D3D12RaytracingProceduralGeometry/DXR-Other.cpp
Thank you!
- Java2D gradient line stroke
-
How can I use CSFML for C programming on Linux?
Can I use CSFML for C programming on linux? I already tried downloading it from https://www.sfml-dev.org/download/csfml , but I can't find out how to install it.
-
On iOS 13, picking between the "display" system font and the "text" system font
I am familiar with the new Apple guidelines that the system fonts should no longer be accessed by the names and only the system API should be used. Beyond this new requirement, it seems like the SF display and text fonts have been merged into one font. The app I work on has user content where the users in the past have freely used SF Display or SF Text at any size and we are hoping to still support this behavior. This appears to no longer be possible. Some code:
UIFont *fontDisplay = [UIFont systemFontOfSize:10]; UIFont *fontText = [UIFont systemFontOfSize:20]; NSLog(@"display font %@ and %@", fontDisplay.fontName, fontDisplay.familyName); NSLog(@"text font %@ and %@", fontText.fontName, fontText.familyName);
On ios12, we get two distinct fonts:
display font .SFUIText and .SF UI Text text font .SFUIDisplay and .SF UI Display
On ios13, we get one font:
display font .SFUI-Regular and .AppleSystemUIFont text font .SFUI-Regular and .AppleSystemUIFont
On ios12, we used to be able to use "UIFont fontWithSize" with either fontDisplay and fontText to get a small point version of Display or a large point version of Text to support what the authors have created. On ios 13, this is no longer possible.
Does anyone know any workarounds for this new behavior?
-
unicode character Robot Face
i'M having some issue showing unicode character Robot Face on different browsers
Here is my code
<Grid data-rows={rows} data-cols={cols}> {grid.map((row, x) => row.map((_, y) => ( <Cell id={`${x}${y}`} data-direction={Helpers.rotationMapper(currentPosition.direction)} > {Helpers.isCurrentPos(x, y, currentPosition.currentPosition) && '\u1F916'} </Cell> )) )} </Grid>
it create a Grid with cell's and in position[0,0] it should display a robot-face but it doesn't render correctly. This is what i'm getting (ᾑ6). I've tried render the unicode character with css (font-family: 'Symbola') but it didn't help.
Any ideas how to solve it?
-
Why does compiling Font Awesome Sass to CSS create a fonts folder in the wrong location?
I'm compiling Font Awesome Sass files to CSS, and it's putting a
fonts
folder with all the font files at the root level of my project, which I don't want.Specifically, I installed the free Font Awesome npm package as follows:
npm install --save-dev @fortawesome/fontawesome-free
I then added the following to a
vendor.scss
file:$fa-font-path: '../../../../public/fonts' !default; @import '~@fortawesome/fontawesome-free/scss/fontawesome'; @import '~@fortawesome/fontawesome-free/scss/brands'; @import '~@fortawesome/fontawesome-free/scss/regular'; @import '~@fortawesome/fontawesome-free/scss/solid';
This is the directory structure of the project:
(Project root) |---fonts (I don't want this one.) |---node_modules | |---@fortawesome | |---fontawesome-free | |---scss | |---_variables.scss (Contains original $fa-font-path being overridden.) |---public | |---css | |---fonts (This is the one I want.) |---src |---sass |---vendor.scss (Contains new $fa-font-path definition and FA Sass imports.)
If I change
$fa-font-path
to'../../../public/fonts' !default;
or'../../public/fonts' !default;
then the build process errors out and won't compile, but'../../../../public/fonts' !default;
puts all the Font Awesome font files in afonts
folder at both the project root level and in thepublic/fonts
folder. Why is it doing this, and more importantly, how can I stop it from creating thefonts
folder at the root level? Thank you. -
I want a java program with tree set that makes a knockout drawing for football teams
User has to enter how many teams participate in tournament (div has to end to 2 teams...final)-drawing with random. The user has to enter the final score of each match (winner goes up to his "father"). Winner will be the "root".Save somehow the score of each match... thank you!!
-
How do I display a score at the top of my screen in pygame?
I am trying to display the score of a platformer game at the top of the screen but every time I run it I get this error : “Text must be a Unicode or bytes” I’ve already looked on the site and the code all looks exactly like what I’ve written but I’m still getting the same error. This is my code so far:
def __init__(self): #this has all the things needed to initialise the game but the only relevant one to my problem is this line self.font_name = pygame.font.match_font(FONT_NAME) def draw(self): self.screen.fill(BLACK) self.all_sprites.draw(self.screen) self.draw_text(self.score, 22, WHITE, WIDTH / 2, 15) pygame.display.flip() def draw_text(self, text, size, colour, x, y): font = pygame.font.Font(self.font_name, size) text_surface = font.render(text, True, colour) text_rect = text_surface.get_rect() text_rect.midtop = (x, y) self.screen.blit(text_surface, text_rect)
All things in capitals have been given values in another file I called settings and then imported to this file.
The issue seems to be with the text_surface line but I have no idea what the problem is.
-
Using turtle module to draw patterns
Just started learning python. I am trying to draw this pattern by the turtle module, not only this one but I am also having trouble when applying loops to draw any kind of patterns (especially when it comes to patterns with different shapes lying inside each other, I just simply do not know where to start and how to organize the functions to draw those kinds of complex patterns like that). Therefore, I usually go step by step knowing that there should be a loop to make the turtle do the same thing all over again. Anyway here is the pattern I'm trying to draw: pattern And here is what I have so far:
import turtle wn = turtle.Screen() t = turtle.Turtle() def pattern(t,clr): t.screen.bgcolor("white") t.pensize(10) for i in range(2): t.pd() t.fd(100) ## t.rt(90) t.fd(100) ## t.rt(90) t.fd(90) ## t.rt(90) t.fd(75) ## t.rt(90) t.fd(70) ## t.rt(90) t.fd(38) ## t.rt(90) t.fd(38) ## t.pu() t.lt(90) t.fd(77) t.pd() t.lt(90) t.fd(38) t.rt(90) t.fd(38) t.rt(90) t.fd(70) t.rt(90) t.fd(75) t.rt(90) t.fd(90) t.rt(90) t.fd(100) t.rt(90) t.fd(100) pattern(t,"black")
Any tips and advices would be much appreciated! Thank you!
-
How to make Flutter app font size independent from device settings?
I needed to make my entire app independed from device's font size settings. I found that I could set
textScaleFactor: 1.0
for every text view manualy. It's a good solution for a few Text widgets, but not good for a big app with dozens of Text widgets. -
Where to use rems ? And where not to?
I have been trying to play good and use REMS where possible for accessibility. So I am using rems everywhere I am using font-size - which seems an obvious choice.
I am trying to find out where else I should be using them and of course where I should not.
I am presuming the size of an image (height and width) should be still done in Pixels otherwise as the font size grows (base) then it would affect the size of the image.
What about size of padding and margins ? Should these be in px or rem ?
I am using a utility to convert pixel to rem, so I am able to still specify a pixel value but of course this meaning that sizes would grow depending on the base font size.
So I am assuming all fonts should be using REM but what else.
I am finding a lot of conflicting information and there doesn't seem to be anything specific ?
Where is it ok to use Pixels (not being converted to rems)
Can anyone help.
-
Showing the age number as red and bolded in JSX code
I have a web page which has a button (Change age), which increases the value of person's age every time it is pressed. How could I make so that when it's value exceedes 10, the number is shown on red backround and and the number itself is shown as bolded? The number should be shown on red background and bolded where it reads below the Change and Change age buttons:
The age is:
I need to use some kind of conditional rendering in JSX with changeBackground function, but I am not sure how. Here is my code:
import React from 'react'; class App extends React.Component { constructor(props) { super(props); this.changeClicked = this.changeClicked.bind(this); this.state = { name : 'jerry', age : 10 } } changeClicked() { this.setState({nimi : 'Anne'}); } changeAge() { //this.setState({age : this.state.age + 1, name : 'Jacob'}) this.setState((prevStatus) => ({age : prevStatus.age + 1})); console.log("Age is " + this.state.age); //this.setState({name : 'Maureen'}) } changeBackground() { this.setState({backgroundColor: 'red'}); } render() { const age = this.state.age; const color = 'white'; return ( <div> { <p style={{color : 'red'}}>name and age information</p> } <h3 style={{backgroundColor : color}}>Name is {this.state.name} and age = {age}</h3> <button onClick={this.changeClicked}>Change</button> <button onClick={() => this.changeAge()}>Change age</button> <p>Age is: {age}</p> <div> </div> <Info nimi={this.state.name} address="Europe" /> </div> ) } } export default App;