- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
在“Pro JavaFX 8:构建桌面、移动和嵌入式 Java 客户端的权威指南”的第 3 章中,一个示例说明了如何直接在 FXML 文件中指定对象。
您可以在本文末尾找到完整的 FXML 文件以及示例中的其他文件。
这是我正在讨论的片段。 sizes
字段使用 fx:factory
属性来指示必须使用工厂方法 Utilities.createList() 创建一个整数列表,然后用三个整数填充该列表.
<sizes>
<Utilities fx:factory="createMyCollection">
<Integer fx:value="1"/>
<Integer fx:value="2"/>
<Integer fx:value="3"/>
</Utilities>
</sizes>
这是 Utilities.java:
package projavafx.fxmlbasicfeatures;
import java.util.ArrayList;
import java.util.List;
public class Utilities {
public static final Double TEN_PCT = 0.1d;
public static final Double TWENTY_PCT = 0.2d;
public static final Double THIRTY_PCT = 0.3d;
public static List<Integer> createList() {
return new ArrayList<>();
}
}
我的问题是:使用这些工厂方法所涉及的一般机制是什么?
我想了解 FXMLLoader 如何知道需要使用 add
方法将三个整数添加到创建的对象中。当然,它必须以某种方式了解List
或者Collection
,但是这些知识在哪里指定呢?它是内置在 FXMLLoader 中吗?如果是这样,如何为用户定义的类提供这样的工厂方法?
我实际上尝试将它与用户定义的类一起使用。我将以下代码片段添加到 Utilities.java,它创建一个 MyCollection
类,该类具有单个方法 add(Integer)
并定义 Utilities.createMyCollection
> 方法:
public class Utilities {
(...)
public static class MyCollection {
private List<Integer> myList = new LinkedList<>();
public void add(Integer o) {
myList.add(o);
}
public String toString() {
return myList.toString();
}
}
public static MyCollection createMyCollection() {
return new MyCollection();
}
(...)
}
但是,当我在 FXML 文件中替换 createMyCollection 时,我收到消息“MyCollections 没有默认属性。请将 MyCollection 内容放入属性元素中。”
这让我想知道如何为用户定义的类声明默认属性,以及 List
如何已经拥有一个默认属性。
这是所有文件(除了上面的 Utilities.java 之外):
FXMLBasicFeatures.fxml:
<?import javafx.scene.paint.Color?>
<?import projavafx.fxmlbasicfeatures.FXMLBasicFeaturesBean?>
<?import projavafx.fxmlbasicfeatures.Utilities?>
<?import java.lang.Double?>
<?import java.lang.Integer?>
<?import java.lang.Long?>
<?import java.util.HashMap?>
<?import java.lang.String?>
<FXMLBasicFeaturesBean name="John Smith"
flag="true"
count="12345"
xmlns:fx="http://javafx.com/fxml/1">
<address>12345 Main St.</address>
<foreground>#ff8800</foreground>
<background>
<Color red="0.0" green="1.0" blue="0.5"/>
</background>
<price>
<Double fx:value="3.1415926"/>
</price>
<discount>
<Utilities fx:constant="TEN_PCT"/>
</discount>
<sizes>
<Utilities fx:factory="createList">
<Integer fx:value="1"/>
<Integer fx:value="2"/>
<Integer fx:value="3"/>
</Utilities>
</sizes>
<profits>
<HashMap q1="1000" q2="1100" q3="1200" a4="1300"/>
</profits>
<fx:define>
<Long fx:id="inv" fx:value="9765625"/>
</fx:define>
<inventory>
<fx:reference source="inv"/>
</inventory>
<products>
<String fx:value="widget"/>
<String fx:value="gadget"/>
<String fx:value="models"/>
</products>
<abbreviations CA="California" NY="New York" FL="Florida" MO="Missouri"/>
</FXMLBasicFeaturesBean>
FXMLBasicFeaturesBean.java:
package projavafx.fxmlbasicfeatures;
import javafx.scene.paint.Color;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class FXMLBasicFeaturesBean {
private String name;
private String address;
private boolean flag;
private int count;
private Color foreground;
private Color background;
private Double price;
private Double discount;
private List<Integer> sizes;
private Map<String, Double> profits;
private Long inventory;
private List<String> products = new ArrayList<String>();
private Map<String, String> abbreviations = new HashMap<>();
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public boolean isFlag() {
return flag;
}
public void setFlag(boolean flag) {
this.flag = flag;
}
public int getCount() {
return count;
}
public void setCount(int count) {
this.count = count;
}
public Color getForeground() {
return foreground;
}
public void setForeground(Color foreground) {
this.foreground = foreground;
}
public Color getBackground() {
return background;
}
public void setBackground(Color background) {
this.background = background;
}
public Double getPrice() {
return price;
}
public void setPrice(Double price) {
this.price = price;
}
public Double getDiscount() {
return discount;
}
public void setDiscount(Double discount) {
this.discount = discount;
}
public List<Integer> getSizes() {
return sizes;
}
public void setSizes(List<Integer> sizes) {
this.sizes = sizes;
}
public Map<String, Double> getProfits() {
return profits;
}
public void setProfits(Map<String, Double> profits) {
this.profits = profits;
}
public Long getInventory() {
return inventory;
}
public void setInventory(Long inventory) {
this.inventory = inventory;
}
public List<String> getProducts() {
return products;
}
public Map<String, String> getAbbreviations() {
return abbreviations;
}
@Override
public String toString() {
return "FXMLBasicFeaturesBean{" +
"name='" + name + '\'' +
",\n\taddress='" + address + '\'' +
",\n\tflag=" + flag +
",\n\tcount=" + count +
",\n\tforeground=" + foreground +
",\n\tbackground=" + background +
",\n\tprice=" + price +
",\n\tdiscount=" + discount +
",\n\tsizes=" + sizes +
",\n\tprofits=" + profits +
",\n\tinventory=" + inventory +
",\n\tproducts=" + products +
",\n\tabbreviations=" + abbreviations +
'}';
}
}
FXMLBasicFeaturesMain.java:
package projavafx.fxmlbasicfeatures;
import javafx.fxml.FXMLLoader;
import java.io.IOException;
public class FXMLBasicFeaturesMain {
public static void main(String[] args) throws IOException {
FXMLBasicFeaturesBean bean = FXMLLoader.load(
FXMLBasicFeaturesMain.class.getResource(
"/projavafx/fxmlbasicfeatures/FXMLBasicFeatures.fxml")
);
System.out.println("bean = " + bean);
}
}
最佳答案
这里实际上存在几个不同的问题。如您所知,基本用法是 FXMLLoader
通过 JavaBean 命名方案查找经典风格的属性。所以如果你有课
public class Bean {
private String text ;
public void setText(String text) {
this.text = text ;
}
public String getText() {
return text ;
}
}
然后(因为该类有一个默认的无参数构造函数),您可以实例化 Bean
在 FXML 中:
<Bean>
您可以调用setText
方法通过引用属性 text
作为属性:
<Bean text="Some text"/>
或作为属性元素:
<Bean>
<text>
<String fx:value="Some text"/>
</text>
</Bean>
java.util.List
的实例得到特殊待遇。如果属性名称与只读 List
匹配属性:即 java.util.List
类型的属性其中有 get...
方法但没有set...
方法中,FXML中的子节点将被传递到相应的List
实例add(...)
方法。
因此,如果我们将这样的属性添加到 Bean
:
import java.util.List ;
import java.util.ArrayList ;
public class Bean {
private String text ;
private List<String> elements ;
public Bean() {
this.elements = new ArrayList<>();
}
public List<String> getElements() {
return elements ;
}
public void setText(String text) {
this.text = text ;
}
public String getText() {
return text ;
}
}
然后我们可以在 FXML 中填充列表:
<Bean text="Some text">
<elements>
<String fx:value="One"/>
<String fx:value="Two"/>
<String fx:value="Three"/>
</elements>
<Bean>
您提到的另一个问题是“默认属性”。您可以使用 @DefaultProperty
指定类的默认属性。类上的注释,并指定被视为默认的属性名称:
import java.util.List ;
import java.util.ArrayList ;
@DefaultProperty("text")
public class Bean {
private String text ;
private List<String> elements ;
public Bean() {
this.elements = new ArrayList<>();
}
public List<String> getElements() {
return elements ;
}
public void setText(String text) {
this.text = text ;
}
public String getText() {
return text ;
}
}
现在,如果您指定实例元素的子元素 <Bean>
在 FXML 中,如果不指定属性,这些将用作默认属性的值:
<Bean>
<String fx:value="Some Text"/>
</Bean>
将调用setText("Some Text")
关于Bean
实例。
当然,您可以结合这些想法并制作 List
实例默认属性(这本质上是布局容器的工作方式: Pane
将 "children"
定义为其默认属性):
import java.util.List ;
import java.util.ArrayList ;
@DefaultProperty("elements")
public class Bean {
private String text ;
private List<String> elements ;
public Bean() {
this.elements = new ArrayList<>();
}
public List<String> getElements() {
return elements ;
}
public void setText(String text) {
this.text = text ;
}
public String getText() {
return text ;
}
}
现在你可以做
<Bean text="Some Text">
<String fx:value="One"/>
<String fx:value="Two" />
<String fx:value="Three" />
</Bean>
将填充 elements
列表为 ["One", "Two", "Three"]
.
关于javafx - FXMLLoader 工厂方法可以用于用户定义的类吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30267070/
我应该执行以下操作: 可能通过服务/工厂,使用 $q(异步)查询 API 以获取大型名称数据集 有另一个服务(也是异步的),它应该只返回上述工厂的元素,如果它们与某个字符串(搜索字段)匹配。目的是缩小
我有一个通用的基类。我有一个实现基类的具体类。 我将如何创建工厂类/方法来交付不同类型的具体类? 举个例子: public class ReceiverBase where T : IInte
我正在查看以下链接中的 Ninject Factory 扩展: http://www.planetgeek.ch/2011/12/31/ninject-extensions-factory-intro
工厂、提供商和服务这三个术语之间有什么区别? 刚刚了解 NHibernate 及其存储库模式(POCO 类等)。 最佳答案 工厂:通过将一堆位组合在一起或基于某种上下文选择类型来组装类 Provide
使用CGLIB我可以做到 final var enhancer = new Enhancer(); enhancer.setUseCache(false); enhancer.setSuperclas
我试图在 Kotlin 中使用伴随对象工厂方法(相当于 Java 中的静态工厂方法)创建一个嵌套内部类。这是我的代码的简化版本。 class OuterClass { var myData:L
我正在为我的大学做一个项目,但遇到了问题。 基本上,该项目由一个客户端-服务器应用程序组成,我想创建一个用于通信的 Packet 类。数据包由 header 和主体组成。现在问题来了。我可以有一些不同
这个问题在这里已经有了答案: Why doesn't polymorphism work without pointers/references? (6 个答案) What is object sl
我正在制作一个套接字工厂。我希望每个外部应用程序都使用 Socket 类的接口(interface),它是几个类(ServerSocketTCP、ClientSocketTCP、ServerSocke
我是 angularjs 的新手,我正在尝试创建一个小型电影数据库。这是我第一次使用工厂,我想确保这是正确的方法,以及如何在另一个功能中使用这个工厂,如下所示? 我希望这个工厂只运行一次,这样我就可以
这个问题在这里已经有了答案: Java inner class and static nested class (28 个答案) 关闭 5 年前。 public class DataFactory
我看过很多关于 C++ 工厂的帖子,但到目前为止我还没有看到解决我的问题的解决方案。 (虽然我可能遗漏了一些东西。) 示例控制台应用程序: #include #include #include
这是一个简单的 C++ 项目,有 2 种设计模式:单例和工厂,sigleton 也是一个模板化类,一个接口(interface) (IHash) 和一个类 (Hash1)。一个简单的工厂类 (Hash
这个问题类似于Factory and generics ,并且可能有相同的答案,但它是不同的。我有一个通用基类,它将由完全独立的 JAR 中的类进行扩展。所述 JAR 应该能够在不更改任何其他代码的情
问题是我需要为传递的类创建一个新实例 有没有办法重写这个函数,让它可以接受任意数量的参数? function createInstance(ofClass, arg1, arg2, arg3, ...
我想用简单的 C++ 语法创建一个简单的工厂方法: void *createObject(const char *str,...) { if(!strcmp("X",str)) retu
经过大约 10 个月的程序化 PHP 学习后,我现在正尝试着手研究基本的 OOP 原则和设计模式。这是一个爱好,我没有那么多时间去追求它,所以请原谅这个问题的水平很低。 我的网站(目前 100% 程序
我有一个简单的问题。 我如何编写一个工厂来定义使用 make() 或 create() 的关系,具体取决于原始调用 make() 还是 create()? 这是我的用例: 我有一个简单的工厂 /**
我正在尝试在延迟加载模块中提供 APP_BASE_HREF 注入(inject) token ,然而,工厂方法根本没有被调用。 在这里https://github.com/MaurizioCascia
我有以下 ast: import { factory as f } from 'typescript' const typeDeclaration = f.createTypeAliasDeclara
我是一名优秀的程序员,十分优秀!